/**
 * Copyright 2014-2021 the original author or authors.
 * <p>
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 * <p>
 * http://www.apache.org/licenses/LICENSE-2.0
 * <p>
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */
package com.webank.webase.front.contractStore.constant;

public class ProxyConstantContext {


    public static final String ENROLL_PROXY_SOURCE = "cHJhZ21hIHNvbGlkaXR5IF4wLjQuMjU7DQoNCmltcG9ydCAiLi9Qcm94eS5zb2wiOw0KaW1wb3J0ICIuL0Vucm9sbFN0b3JhZ2VTdGF0ZWZ1bC5zb2wiOw0KDQovKioNCiAqIOeZu+iusOWFpeWPo+WQiOe6pg0KICovDQpjb250cmFjdCBFbnJvbGxQcm94eSBpcyBFbnJvbGxTdG9yYWdlU3RhdGVmdWwsIFByb3h5IHsNCg0KDQogICAgLy8vLy8vLy8vLy8vLy8vDQogICAgLy8vLyBFdmVudA0KICAgIC8vLy8vLy8vLy8vLy8vLw0KICAgIGV2ZW50IFNldFN0b3JhZ2UoYWRkcmVzcyBvcGVyYXRvciwgYWRkcmVzcyBlbnJvbGxTdG9yYWdlKTsNCg0KICAgIC8vLy8vLy8vLy8vLy8vLw0KICAgIC8vLy8gRnVuY3Rpb25zDQogICAgLy8vLy8vLy8vLy8vLy8vDQoNCiAgICAvKioNCiAgICAqIEBub3RpY2Ug6K6+572u5a2Y5YKoDQogICAgKiBAZGV2IOmZkOWQiOe6pueuoeeQhuWRmOiwg+eUqA0KICAgICogQHBhcmFtIF9zdG9yYWdlQWRkciDnmbvorrDlrZjlgqjlkIjnuqYNCiAgICAqLw0KICAgIGZ1bmN0aW9uIHNldFN0b3JhZ2UoYWRkcmVzcyBfc3RvcmFnZUFkZHIpIGV4dGVybmFsIG9ubHlPd25lciB7DQoNCiAgICAgICAgcmVxdWlyZShfc3RvcmFnZUFkZHIgIT0gYWRkcmVzcygwKSwgIlByb3h5OiBzdG9yYWdlIGFkZHJlc3Mgc2hvdWxkIG5vdCBiZSAweCIpOw0KICAgICAgICByZXF1aXJlKEFkZHJlc3MuaXNDb250cmFjdChfc3RvcmFnZUFkZHIpLCAiUHJveHk6IENhbm5vdCBzZXQgYSBwcm94eSBzdG9yYWdlIHRvIGEgbm9uLWNvbnRyYWN0IGFkZHJlc3MiKTsNCg0KICAgICAgICBlbnJvbGxTdG9yYWdlID0gRW5yb2xsU3RvcmFnZShfc3RvcmFnZUFkZHIpOw0KICAgICAgICBzdG9yYWdlQWRkckxpc3QucHVzaChfc3RvcmFnZUFkZHIpOw0KICAgICAgICBlbWl0IFNldFN0b3JhZ2UobXNnLnNlbmRlciwgX3N0b3JhZ2VBZGRyKTsNCiAgICB9DQoNCiAgICAvKioNCiAgICAqIEBub3RpY2Ug6L+U5Zue5omA5pyJ55qE5a2Y5YKo5ZCI57qm5Zyw5Z2A5YiX6KGoDQogICAgKi8NCiAgICBmdW5jdGlvbiBnZXRTdG9yYWdlVmVyc2lvbnMoKSB2aWV3IHJldHVybnMgKHN0cmluZyBtZW1vcnkgcmVzdWx0KXsNCiAgICAgICAgcmVzdWx0PSJ7IjsNCiAgICAgICAgZm9yKHVpbnQgaSA9IDA7IGkgPCBzdG9yYWdlQWRkckxpc3QubGVuZ3RoOyBpKyspIHsNCiAgICAgICAgICAgIHJlc3VsdCA9IHJlc3VsdC50b1NsaWNlKCkuY29uY2F0KGFkZHJlc3NUb1N0cmluZyhzdG9yYWdlQWRkckxpc3RbaV0pLnRvU2xpY2UoKSk7DQogICAgICAgICAgICBpZihpICE9IChzdG9yYWdlQWRkckxpc3QubGVuZ3RoLTEpKSB7DQogICAgICAgICAgICAgICAgcmVzdWx0ID0gcmVzdWx0LnRvU2xpY2UoKS5jb25jYXQoIiwiLnRvU2xpY2UoKSk7DQogICAgICAgICAgICB9DQogICAgICAgIH0NCiAgICAgICAgcmVzdWx0ID0gcmVzdWx0LnRvU2xpY2UoKS5jb25jYXQoIn0iLnRvU2xpY2UoKSk7DQogICAgfQ0KfQ0K";
    public static final String ENROLL_CONTROLLER_SOURCE = "cHJhZ21hIHNvbGlkaXR5IF4wLjQuMjU7DQpwcmFnbWEgZXhwZXJpbWVudGFsIEFCSUVuY29kZXJWMjsNCg0KaW1wb3J0ICIuL093bmFibGUuc29sIjsNCmltcG9ydCAiLi9FbnJvbGxTdG9yYWdlU3RhdGVmdWwuc29sIjsNCmltcG9ydCAiLi9UYWJsZS5zb2wiOw0KaW1wb3J0ICIuL1N0cmluZ3Muc29sIjsNCg0KDQoNCi8qKg0KICog55m76K6w6YC76L6R5ZCI57qmDQogKi8NCmNvbnRyYWN0IEVucm9sbENvbnRyb2xsZXIgaXMgRW5yb2xsU3RvcmFnZVN0YXRlZnVsLCBPd25hYmxlIHsNCiAgICANCiAgICB1c2luZyBTdHJpbmdzIGZvciAqOw0KDQogICAgLy8vLy8vLy8vLy8vLy8vDQogICAgLy8vLyBFdmVudA0KICAgIC8vLy8vLy8vLy8vLy8vLw0KDQogICAgZXZlbnQgQ3JlYXRlKHN0cmluZyB0YWJsZU5hbWUpOw0KICAgIGV2ZW50IFB1dChzdHJpbmcgdGFibGVOYW1lLCBzdHJpbmcga2V5LCBzdHJpbmcgdmFsdWUpOw0KICAgIGV2ZW50IFJlbW92ZShzdHJpbmcgdGFibGVOYW1lLCBzdHJpbmcga2V5KTsNCiAgICBldmVudCBNdWx0aVB1dEpzb24oc3RyaW5nIHRhYmxlTmFtZSwgc3RyaW5nIGtleXMsIHN0cmluZyB2YWx1ZXMsIHN0cmluZyByZXN1bHQpOw0KDQogICAgLy8vLy8vLy8vLy8vLy8vDQogICAgLy8vLyBGdW5jdGlvbnMNCiAgICAvLy8vLy8vLy8vLy8vLy8NCg0KICAgIC8qKg0KICAgICogQG5vdGljZSDliqjmgIHlu7rooagNCiAgICAqIEBwYXJhbSB0YWJsZU5hbWUg6KGo5ZCNDQogICAgKi8NCiAgICBmdW5jdGlvbiBjcmVhdGUoc3RyaW5nIHRhYmxlTmFtZSkgZXh0ZXJuYWwgew0KDQogICAgICAgIHJlcXVpcmUoZW5yb2xsU3RvcmFnZS5TdG9yYWdlQ3JlYXRlKHRhYmxlTmFtZSkgPT0gaW50KDApLCAiRW5yb2xsQ29udHJvbGxlcjogY3JlYXRlVGFibGUgZXJyb3IiKTsNCg0KICAgICAgICBlbWl0IENyZWF0ZSh0YWJsZU5hbWUpOw0KICAgIH0NCg0KICAgIC8qKg0KICAgICogQG5vdGljZSDmt7vliqDkv6Hmga/vvIzoh6rliqjljLrliIbmmK/ms6jlhozkv6Hmga/ov5jmmK/mm7TmlrDkv6Hmga8NCiAgICAqIEBwYXJhbSB0YWJsZU5hbWUg6KGo5ZCNDQogICAgKiBAcGFyYW0ga2V5IOS4u+mUrg0KICAgICogQHBhcmFtIHZhbHVlIOWAvA0KICAgICovDQogICAgZnVuY3Rpb24gcHV0KHN0cmluZyB0YWJsZU5hbWUsIHN0cmluZyBrZXksIHN0cmluZyB2YWx1ZSkgZXh0ZXJuYWwgew0KDQogICAgICAgIGludCBfcmVzdWx0IDsNCiAgICAgICAgc3RyaW5nIG1lbW9yeSAgX2tleTsNCiAgICAgICAgc3RyaW5nIG1lbW9yeSAgX3ZhbHVlIDsNCiAgICAgICAgDQogICAgICAgIChfcmVzdWx0LCBfa2V5LCBfdmFsdWUpID0gZW5yb2xsU3RvcmFnZS5TdG9yYWdlU2VsZWN0KHRhYmxlTmFtZSwga2V5KTsNCg0KICAgICAgICByZXF1aXJlKGtlY2NhazI1NihfdmFsdWUpICE9IGtlY2NhazI1Nih2YWx1ZSksIkVucm9sbENvbnRyb2xsZXI6IHNhbWUgdmFsdWUsIG5vdCBuZWVkIHB1dCIpOw0KDQogICAgICAgIHJlcXVpcmUoZW5yb2xsU3RvcmFnZS5TdG9yYWdlUHV0KHRhYmxlTmFtZSwga2V5LCB2YWx1ZSkgPT0gaW50KDEpLCAiRW5yb2xsQ29udHJvbGxlcjogcHV0IGluZm8gZXJyb3IiKTsNCg0KICAgICAgICBlbWl0IFB1dCh0YWJsZU5hbWUsIGtleSwgdmFsdWUpOw0KICAgIH0NCg0KICAgIC8qDQogICAgKiBAbm90aWNlIOWcqOihqOS4reWIoOmZpGtleeWvueW6lOeahOiusOW9lQ0KICAgICogICAgICAgICDliKDpmaTmiYDmnInniYjmnKzkuK1rZXnlr7nlupTnmoTorrDlvZUNCiAgICAqDQogICAgKiBAcGFyYW0gdGFibGVOYW1lIOihqOWQjQ0KICAgICogQHBhcmFtIGtleVZhbHVlIOS4u+mUrg0KICAgICovDQogICAgZnVuY3Rpb24gcmVtb3ZlKHN0cmluZyB0YWJsZU5hbWUsIHN0cmluZyBrZXkpIGV4dGVybmFsIHsNCg0KICAgICAgICByZXF1aXJlKGVucm9sbFN0b3JhZ2UuU3RvcmFnZVJlbW92ZSh0YWJsZU5hbWUsIGtleSkgPT0gaW50KDEpLCAiRW5yb2xsQ29udHJvbGxlcjogcmVtb3ZlIGluZm8gZXJyb3IiKTsNCg0KICAgICAgICBlbWl0IFJlbW92ZSh0YWJsZU5hbWUsIGtleSk7DQogICAgfQ0KDQogICAgLyoqDQogICAgKiBAbm90aWNlIOiOt+WPlumTvuS4iuS/oeaBrw0KICAgICogQHBhcmFtIHRhYmxlTmFtZSDooajlkI0NCiAgICAqIEBwYXJhbSBrZXkg5Li76ZSuDQogICAgKi8NCiAgICBmdW5jdGlvbiBnZXQoc3RyaW5nICB0YWJsZU5hbWUsIHN0cmluZyAga2V5KSB2aWV3IHJldHVybnMoDQogICAgICAgIGludCBfcmVzdWx0ICxzdHJpbmcgIF9rZXksc3RyaW5nICBfdmFsdWUpew0KDQogICAgICAgIHJldHVybiBlbnJvbGxTdG9yYWdlLlN0b3JhZ2VTZWxlY3QodGFibGVOYW1lLCBrZXkpOw0KICAgIH0NCg0KfQ==";
    public static final String ENROLL_STORAGE_SOURCE = "cHJhZ21hIHNvbGlkaXR5IF4wLjQuMjU7DQpwcmFnbWEgZXhwZXJpbWVudGFsIEFCSUVuY29kZXJWMjsNCg0KaW1wb3J0ICIuL1RhYmxlLnNvbCI7DQppbXBvcnQgIi4vQmFzZVN0b3JhZ2Uuc29sIjsNCmltcG9ydCAiLi9TdHJpbmdzLnNvbCI7DQoNCi8qKg0KICog55m76K6w5a2Y5YKo5ZCI57qmDQogKi8NCmNvbnRyYWN0IEVucm9sbFN0b3JhZ2UgaXMgQmFzZVN0b3JhZ2Ugew0KICAgIHVzaW5nIFN0cmluZ3MgZm9yICo7DQoJDQogICAgLy8gdGFibGXliJfooagNCiAgICBzdHJpbmdbXSBpbnRlcm5hbCB0YWJsZUxpc3Q7DQogICAgLy8gdGFibGXorrDlvZXnmoTmnaHnm67mlbANCiAgICBtYXBwaW5nKHN0cmluZyA9PiB1aW50KSBpbnRlcm5hbCB0YWJsZVJlY29yZHM7DQogICAgLyoqDQogICAgKiBAcmV0dXJuIHRhYmxl5YiX6KGoDQogICAgKi8NCiAgICBmdW5jdGlvbiBnZXRUYWJsZUxpc3QoKSBwdWJsaWMgdmlldyByZXR1cm5zIChzdHJpbmdbXSkgew0KICAgICAgICByZXR1cm4gdGFibGVMaXN0Ow0KICAgIH0NCg0KICAgIC8qKg0KICAgICogQHJldHVybiB0YWJsZeS4reaTjeS9nOeahOadoeebruaVsA0KICAgICovDQogICAgZnVuY3Rpb24gZ2V0VGFibGVSZWNvcmRzKHN0cmluZyBrZXkpIHB1YmxpYyB2aWV3IHJldHVybnMgKHVpbnQpIHsNCiAgICAgICAgcmV0dXJuIHRhYmxlUmVjb3Jkc1trZXldOw0KICAgIH0NCg0KICAgIC8qKg0KICAgICogQG5vdGljZSDliqjmgIHliJvlu7rooagNCiAgICAqIEBwYXJhbSB0YWJsZU5hbWUg6KGo55qE5ZCN56ewDQogICAgKiDooajnu5PmnoTvvJoNCiAgICAqICstLS0tLS0tLS0tLS0tLSstLS0tLS0tLS0tLS0tLS0tLS0tLS0rLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLSsNCiAgICAqIHwgRmllbGQgICAgICAgIHwgVHlwZSAgICAgICAgICAgICAgICB8IERlc2MgICAgICAgICAgICAgICAgICAgIHwNCiAgICAqICstLS0tLS0tLS0tLS0tLSstLS0tLS0tLS0tLS0tLS0tLS0tLS0rLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLSsNCiAgICAqIHwga2V5ICAgICAgICAgIHwgc3RyaW5nICAgICAgICAgICAgICB8IOS4u+mUriAgICAgICAgICAgICAgICAgICAgIHwNCiAgICAqIHwgdmFsdWUgICAgICAgIHwgc3RyaW5nICAgICAgICAgICAgICB8IOWvueW6lHZhbHVlICAgICAgICAgICAgICAgIHwNCiAgICAqICstLS0tLS0tLS0tLS0tLSstLS0tLS0tLS0tLS0tLS0tLS0tLS0rLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLSsNCiAgICAqICBjb3VudCA9IDAg6KGo56S65oiQ5Yqf5Yib5bu6DQogICAgKiAg5YW25LuW5YC86KGo56S65Yib5bu65aSx6LSlDQogICAgKi8NCiAgICBmdW5jdGlvbiBTdG9yYWdlQ3JlYXRlKHN0cmluZyBtZW1vcnkgdGFibGVOYW1lKXB1YmxpYyBvbmx5UHJveHkgcmV0dXJucyhpbnQpIHsNCiAgICAgICAgVGFibGVGYWN0b3J5IHRmID0gVGFibGVGYWN0b3J5KDB4MTAwMSk7DQogICAgICAgIGludCBjb3VudCA9IHRmLmNyZWF0ZVRhYmxlKHRhYmxlTmFtZSwgImtleSIsICJ2YWx1ZSIpOw0KDQogICAgICAgIHRhYmxlTGlzdC5wdXNoKHRhYmxlTmFtZSk7DQogICAgICAgIGVtaXQgQ3JlYXRlUmVzdWx0KGNvdW50KTsNCiAgICAgICAgDQogICAgICAgIHJldHVybiBjb3VudDsNCiAgICB9DQoNCiAgICAvKioNCiAgICAqIEBub3RpY2Ug5o+S5YWl5pWw5o2uDQogICAgKiBAZGV2IOmZkOWFpeWPo+WQiOe6puiwg+eUqA0KICAgICogQHBhcmFtIHRhYmxlTmFtZSDooajnmoTlkI3np7ANCiAgICAqIEBwYXJhbSBrZXkgICAgICAg5Li76ZSuDQogICAgKiBAcGFyYW0gdmFsdWUgICAgIOWvueW6lHZhbHVlDQogICAgKiBjb3VudCA9IDEgIOihqOekuuaPkuWFpeaIkOWKnw0KICAgICogY291bnQgPSAtMSDooajnpLprZXnlt7LlrZjlnKgNCiAgICAqIOWFtuS7luWAvCDooajnpLrmj5LlhaXlpLHotKUNCiAgICAqLw0KICAgIGZ1bmN0aW9uIFN0b3JhZ2VJbnNlcnQoc3RyaW5nIG1lbW9yeSB0YWJsZU5hbWUsIHN0cmluZyBtZW1vcnkga2V5LCBzdHJpbmcgbWVtb3J5IHZhbHVlKXB1YmxpYyBvbmx5UHJveHkgcmV0dXJucyhpbnQpIHsNCiAgICAgICAgVGFibGVGYWN0b3J5IHRmID0gVGFibGVGYWN0b3J5KDB4MTAwMSk7DQogICAgICAgIFRhYmxlIHRhYmxlID0gdGYub3BlblRhYmxlKHRhYmxlTmFtZSk7DQoNCiAgICAgICAgaW50IGNvdW50ID0gMCA7DQogICAgICAgIGlmKF9pc0tleUV4aXN0KHRhYmxlLCBrZXkpKXsNCiAgICAgICAgICAgIGNvdW50ID0gLTEgOw0KICAgICAgICAgICAgdGFibGVSZWNvcmRzW3RhYmxlTmFtZS50b1NsaWNlKCkuY29uY2F0KCJfSW5zZXJ0X0JBRCIudG9TbGljZSgpKV0gKz0gMTsgDQogICAgICAgIH1lbHNlew0KICAgICAgICAgICAgRW50cnkgZW50cnkgPSB0YWJsZS5uZXdFbnRyeSgpOw0KICAgICAgICAgICAgZW50cnkuc2V0KCJrZXkiLCBrZXkpOw0KICAgICAgICAgICAgZW50cnkuc2V0KCJ2YWx1ZSIsIHZhbHVlKTsNCiAgICAgICAgICAgIGNvdW50ID0gdGFibGUuaW5zZXJ0KGtleSwgZW50cnkpOw0KICAgICAgICAgICAgdGFibGVSZWNvcmRzW3RhYmxlTmFtZS50b1NsaWNlKCkuY29uY2F0KCJfSW5zZXJ0X09LIi50b1NsaWNlKCkpXSArPSAxOyANCiAgICAgICAgfQ0KICAgICAgICBlbWl0IEluc2VydFJlc3VsdChjb3VudCk7DQogICAgICAgIHJldHVybiBjb3VudDsNCiAgICB9DQoNCiAgICAvKioNCiAgICAqIEBub3RpY2Ug6YCa6L+Ha2V55p+l6K+i5pWw5o2uDQogICAgKiBAcGFyYW0gdGFibGVOYW1lIOihqOeahOWQjeensA0KICAgICogQHBhcmFtIGtleSAgICAgICDkuLvplK4NCiAgICAqDQogICAgKiByZXN1bHQgPSAgMCDooajnpLrmn6Xor6LmiJDlip8NCiAgICAqIHJlc3VsdCA9IC0xIOihqOekuuafpeivouWksei0pQ0KICAgICovDQogICAgZnVuY3Rpb24gU3RvcmFnZVNlbGVjdChzdHJpbmcgbWVtb3J5IHRhYmxlTmFtZSwgIHN0cmluZyBtZW1vcnkga2V5KSBwdWJsaWMgdmlldyByZXR1cm5zKA0KICAgICAgICBpbnQgX3Jlc3VsdCAsc3RyaW5nIG1lbW9yeSBfa2V5LHN0cmluZyBtZW1vcnkgX3ZhbHVlDQogICAgKXsNCiAgICAgICAgVGFibGVGYWN0b3J5IHRmID0gVGFibGVGYWN0b3J5KDB4MTAwMSk7DQogICAgICAgIFRhYmxlIHRhYmxlID0gdGYub3BlblRhYmxlKHRhYmxlTmFtZSk7DQoNCiAgICAgICAgaWYoX2lzS2V5RXhpc3QodGFibGUsIGtleSkpew0KICAgICAgICAgICAgQ29uZGl0aW9uIGNvbmRpdGlvbiA9IHRhYmxlLm5ld0NvbmRpdGlvbigpOw0KICAgICAgICAgICAgRW50cnkgZW50cnkgPSB0YWJsZS5zZWxlY3Qoa2V5LCBjb25kaXRpb24pLmdldChpbnQoMCkpOw0KICAgICAgICAgICAgX3Jlc3VsdCA9IDAgOw0KICAgICAgICAgICAgKF9rZXksIF92YWx1ZSkgPSBfcmV0dXJuRGF0YShlbnRyeSk7DQogICAgICAgIH1lbHNlew0KICAgICAgICAgICAgX3Jlc3VsdD0gLTEgOw0KICAgICAgICAgICAgX2tleT0ga2V5IDsNCiAgICAgICAgICAgIF92YWx1ZT0gIiIgOw0KICAgICAgICB9DQogICAgfQ0KDQogICAgLyoqDQogICAgKiBAbm90aWNlIOmAmui/h2tleea3u+WKoOaVsOaNru+8jOiHquWKqOWMuuWIhuaYr+azqOWGjOi/mOaYr+abtOaWsA0KICAgICogQHBhcmFtIHRhYmxlTmFtZSDooajnmoTlkI3np7ANCiAgICAqIEBwYXJhbSBrZXkgICAgICAg5Li76ZSuDQogICAgKiBAcGFyYW0gdmFsdWUgICAgIOWvueW6lHZhbHVlDQogICAgKg0KICAgICogY291bnQgPSAgMSDooajnpLrmt7vliqDmiJDlip8NCiAgICAqIOWFtuS7luWAvOihqOekuuabtOaWsOWksei0pQ0KICAgICovDQogICAgZnVuY3Rpb24gU3RvcmFnZVB1dChzdHJpbmcgbWVtb3J5IHRhYmxlTmFtZSwgc3RyaW5nIG1lbW9yeSBrZXksIHN0cmluZyBtZW1vcnkgdmFsdWUpIHB1YmxpYyBvbmx5UHJveHkgcmV0dXJucyhpbnQpIHsNCiAgICAgICAgVGFibGVGYWN0b3J5IHRmID0gVGFibGVGYWN0b3J5KDB4MTAwMSk7DQogICAgICAgIFRhYmxlIHRhYmxlID0gdGYub3BlblRhYmxlKHRhYmxlTmFtZSk7DQogICAgICAgIGludCBjb3VudCA9IDAgOw0KDQogICAgICAgICggaW50IF9yZXN1bHQsICwgc3RyaW5nIG1lbW9yeSBfdmFsdWUgKSA9IFN0b3JhZ2VTZWxlY3QodGFibGVOYW1lLCBrZXkpOw0KICAgICAgICBFbnRyeSBlbnRyeSA9IHRhYmxlLm5ld0VudHJ5KCk7DQogICAgICAgIGlmKF9yZXN1bHQgPT0gMCApew0KICAgICAgICAgICAgZW50cnkuc2V0KCJ2YWx1ZSIsIHZhbHVlKTsNCiAgICAgICAgICAgIENvbmRpdGlvbiBjb25kaXRpb24gPSB0YWJsZS5uZXdDb25kaXRpb24oKTsNCiAgICAgICAgICAgIGNvdW50ID0gdGFibGUudXBkYXRlKGtleSwgZW50cnksIGNvbmRpdGlvbik7DQogICAgICAgIH1lbHNlew0KICAgICAgICAgICAgZW50cnkuc2V0KCJrZXkiLCBrZXkpOw0KICAgICAgICAgICAgZW50cnkuc2V0KCJ2YWx1ZSIsIHZhbHVlKTsNCiAgICAgICAgICAgIGNvdW50ID0gdGFibGUuaW5zZXJ0KGtleSwgZW50cnkpOw0KICAgICAgICB9DQoNCiAgICAgICAgdGFibGVSZWNvcmRzW3RhYmxlTmFtZS50b1NsaWNlKCkuY29uY2F0KCJfUHV0Ii50b1NsaWNlKCkpXSArPSAxOw0KICAgICAgICBlbWl0IFB1dFJlc3VsdChfcmVzdWx0LCBjb3VudCk7DQogICAgICAgIHJldHVybiBjb3VudDsNCiAgICB9DQoNCiAgICAvKioNCiAgICAqIEBub3RpY2Ug6YCa6L+Ha2V55pu05paw5pWw5o2uDQogICAgKiBAcGFyYW0gdGFibGVOYW1lIOihqOeahOWQjeensA0KICAgICogQHBhcmFtIGtleSAgICAgICDkuLvplK4NCiAgICAqIEBwYXJhbSB2YWx1ZSAgICAg5a+55bqUdmFsdWUNCiAgICAqDQogICAgKiBjb3VudCA9ICAxIOihqOekuuabtOaWsOaIkOWKnw0KICAgICogY291bnQgPSAtMSDooajnpLprZXnkuI3lrZjlnKgNCiAgICAqIOWFtuS7luWAvOihqOekuuabtOaWsOWksei0pQ0KICAgICovDQogICAgZnVuY3Rpb24gU3RvcmFnZVVwZGF0ZShzdHJpbmcgbWVtb3J5IHRhYmxlTmFtZSwgc3RyaW5nIG1lbW9yeSBrZXksIHN0cmluZyBtZW1vcnkgdmFsdWUpIHB1YmxpYyBvbmx5UHJveHkgcmV0dXJucyhpbnQpIHsNCiAgICAgICAgVGFibGVGYWN0b3J5IHRmID0gVGFibGVGYWN0b3J5KDB4MTAwMSk7DQogICAgICAgIFRhYmxlIHRhYmxlID0gdGYub3BlblRhYmxlKHRhYmxlTmFtZSk7DQogICAgICAgIGludCBjb3VudCA9IDAgOw0KDQogICAgICAgICggaW50IF9yZXN1bHQsICwgc3RyaW5nIG1lbW9yeSBfdmFsdWUgKSA9IFN0b3JhZ2VTZWxlY3QodGFibGVOYW1lLCBrZXkpOw0KICAgICAgICBpZihfcmVzdWx0ID09IDAgKXsNCiAgICAgICAgICAgIEVudHJ5IGVudHJ5ID0gdGFibGUubmV3RW50cnkoKTsNCiAgICAgICAgICAgIGVudHJ5LnNldCgidmFsdWUiLCB2YWx1ZSk7DQogICAgICAgICAgICBDb25kaXRpb24gY29uZGl0aW9uID0gdGFibGUubmV3Q29uZGl0aW9uKCk7DQogICAgICAgICAgICBjb3VudCA9IHRhYmxlLnVwZGF0ZShrZXksIGVudHJ5LCBjb25kaXRpb24pOw0KICAgICAgICAgICAgdGFibGVSZWNvcmRzW3RhYmxlTmFtZS50b1NsaWNlKCkuY29uY2F0KCJfVXBkYXRlX09LIi50b1NsaWNlKCkpXSArPSAxOyAgICANCiAgICAgICAgfWVsc2V7DQogICAgICAgICAgICBjb3VudCA9IC0xOw0KICAgICAgICAgICAgdGFibGVSZWNvcmRzW3RhYmxlTmFtZS50b1NsaWNlKCkuY29uY2F0KCJfVXBkYXRlX0JBRCIudG9TbGljZSgpKV0gKz0gMTsgICAgCSAgICANCiAgICAgICAgfQ0KICAgICAgICANCiAgICAgICAgZW1pdCBVcGRhdGVSZXN1bHQoY291bnQpOw0KICAgICAgICByZXR1cm4gY291bnQ7DQogICAgfQ0KDQogICAgLyoqDQogICAgKiBAbm90aWNlIOmAmui/h2tleeWIoOmZpOaVsOaNrg0KICAgICogQHBhcmFtIHRhYmxlTmFtZSDooajnmoTlkI3np7ANCiAgICAqIEBwYXJhbSBrZXkgICAgICAg5Li76ZSuDQogICAgKg0KICAgICogY291bnQgPSAgMSDmoIfor4bliKDpmaTmiJDlip8NCiAgICAqIGNvdW50ID0gLTEg6KGo56S6a2V55LiN5a2Y5ZyoDQogICAgKiDlhbbku5blgLzooajnpLrliKDpmaTlpLHotKUNCiAgICAqLw0KICAgIGZ1bmN0aW9uIFN0b3JhZ2VSZW1vdmUoc3RyaW5nIG1lbW9yeSB0YWJsZU5hbWUsIHN0cmluZyBtZW1vcnkga2V5KSBwdWJsaWMgb25seVByb3h5IHJldHVybnMoaW50KXsNCiAgICAgICAgVGFibGVGYWN0b3J5IHRmID0gVGFibGVGYWN0b3J5KDB4MTAwMSk7DQogICAgICAgIFRhYmxlIHRhYmxlID0gdGYub3BlblRhYmxlKHRhYmxlTmFtZSk7DQogICAgICAgIGludCBjb3VudCA9IDAgOw0KICAgICAgICBpZihfaXNLZXlFeGlzdCh0YWJsZSwga2V5KSl7DQogICAgICAgICAgICBDb25kaXRpb24gY29uZGl0aW9uID0gdGFibGUubmV3Q29uZGl0aW9uKCk7DQogICAgICAgICAgICBjb3VudCA9IHRhYmxlLnJlbW92ZShrZXksIGNvbmRpdGlvbik7DQogICAgICAgICAgICB0YWJsZVJlY29yZHNbdGFibGVOYW1lLnRvU2xpY2UoKS5jb25jYXQoIl9SZW1vdmVfT0siLnRvU2xpY2UoKSldICs9IDE7DQogICAgICAgIH1lbHNlew0KICAgICAgICAgICAgY291bnQgPSAtMTsNCiAgICAgICAgICAgIHRhYmxlUmVjb3Jkc1t0YWJsZU5hbWUudG9TbGljZSgpLmNvbmNhdCgiX1JlbW92ZV9CQUQiLnRvU2xpY2UoKSldICs9IDE7CSAgICANCiAgICAgICAgfQ0KCQ0KICAgICAgICBlbWl0IFJlbW92ZVJlc3VsdChjb3VudCk7DQogICAgICAgIHJldHVybiBjb3VudDsNCiAgICB9DQoNCg0KICAgIC8qKg0KICAgICogQG5vdGljZSDliKTor7trZXnlgLzmmK/lkKblrZjlnKgNCiAgICAqIEBwYXJhbSB0YWJsZU5hbWUg6KGo55qE5ZCN56ewDQogICAgKiBAcGFyYW0ga2V5ICAgICAgIOS4u+mUrg0KICAgICovDQogICAgZnVuY3Rpb24gaXNLZXlFeGlzdChzdHJpbmcgdGFibGVOYW1lLCBzdHJpbmcga2V5KSBleHRlcm5hbCB2aWV3IHJldHVybnMoYm9vbCkgew0KICAgICAgICBUYWJsZUZhY3RvcnkgdGYgPSBUYWJsZUZhY3RvcnkoMHgxMDAxKTsNCiAgICAgICAgVGFibGUgdGFibGUgPSB0Zi5vcGVuVGFibGUodGFibGVOYW1lKTsNCg0KICAgICAgICByZXR1cm4gX2lzS2V5RXhpc3QodGFibGUsIGtleSk7DQogICAgfQ0KDQogICAgZnVuY3Rpb24gX2lzS2V5RXhpc3QoVGFibGUgX3RhYmxlLCBzdHJpbmcgbWVtb3J5IF9pZCkgaW50ZXJuYWwgdmlldyByZXR1cm5zKGJvb2wpIHsNCiAgICAgICAgQ29uZGl0aW9uIGNvbmRpdGlvbiA9IF90YWJsZS5uZXdDb25kaXRpb24oKTsNCiAgICAgICAgcmV0dXJuIF90YWJsZS5zZWxlY3QoX2lkLCBjb25kaXRpb24pLnNpemUoKSAhPSBpbnQoMCk7DQogICAgfQ0KDQoNCiAgICBmdW5jdGlvbiBfcmV0dXJuRGF0YShFbnRyeSBfZW50cnkpIGludGVybmFsIHZpZXcgcmV0dXJucygNCiAgICAgICAgc3RyaW5nIG1lbW9yeSBfa2V5LA0KICAgICAgICBzdHJpbmcgbWVtb3J5IF92YWx1ZQ0KICAgICl7DQogICAgICAgIF9rZXkgPSBfZW50cnkuZ2V0U3RyaW5nKCJrZXkiKTsNCiAgICAgICAgX3ZhbHVlID0gX2VudHJ5LmdldFN0cmluZygidmFsdWUiKTsNCiAgICB9DQp9DQo=";
    public static final String ENROLL_STORAGE_STATEFUL_SOURCE = "cHJhZ21hIHNvbGlkaXR5IF4wLjQuMjU7DQoNCmltcG9ydCAiLi9FbnJvbGxTdG9yYWdlLnNvbCI7DQoNCi8qKg0KICog55m76K6w5ZCI57qm6ZyA6KaB5byV5YWl55qE5a2Y5YKo5ZCI57qmDQogKi8NCmNvbnRyYWN0IEVucm9sbFN0b3JhZ2VTdGF0ZWZ1bCB7DQoNCiAgICAvLyDlrZjlgqjlkIjnuqbniYjmnKzliJfooagNCiAgICBhZGRyZXNzW10gcHVibGljIHN0b3JhZ2VBZGRyTGlzdDsNCg0KICAgIEVucm9sbFN0b3JhZ2UgcHVibGljIGVucm9sbFN0b3JhZ2U7DQp9";
    public static final String PROXY_SOURCE = "cHJhZ21hIHNvbGlkaXR5IF4wLjQuMjU7DQoNCmltcG9ydCAiLi9Pd25hYmxlLnNvbCI7DQppbXBvcnQgIi4vQWRkcmVzcy5zb2wiOw0KaW1wb3J0ICIuL1N0cmluZ3Muc29sIjsNCi8qKg0KICog5YWl5Y+j5ZCI57qm77yM55So5LqO6L2s5Y+R5Lqk5piT6Iez6YC76L6R5ZCI57qmDQogKi8NCmNvbnRyYWN0IFByb3h5IGlzIE93bmFibGUgew0KCXVzaW5nIFN0cmluZ3MgZm9yICo7DQoNCgkvLyDniYjmnKzlr7nlupTnmoTmjqfliLblkIjnuqblnLDlnYAg54mI5pys5Y+3ID0+IOaOp+WItuWQiOe6puWcsOWdgA0KCW1hcHBpbmcoc3RyaW5nID0+IGFkZHJlc3MpIGludGVybmFsIF92ZXJzaW9uczsNCg0KCS8vIOeJiOacrOWIl+ihqA0KCXN0cmluZ1tdIHB1YmxpYyB2ZXJzaW9uTGlzdDsNCg0KCS8vIOW9k+WJjeeJiOacrA0KCXN0cmluZyBwdWJsaWMgdmVyc2lvbjsNCg0KCS8vLy8vLy8vLy8vLy8vLw0KCS8vLy8gRXZlbnQNCgkvLy8vLy8vLy8vLy8vLy8NCg0KCS8vIOS6i+S7tu+8jOabtOaWsOWQjuinpuWPkQ0KCWV2ZW50IFVwZ3JhZGVkKHN0cmluZyBuZXdWZXJzaW9uLCBhZGRyZXNzIG5ld0ltcGxlbWVudGF0aW9uKTsNCgkvLy8vLy8vLy8vLy8vLy8NCgkvLy8vIEZ1bmN0aW9ucw0KCS8vLy8vLy8vLy8vLy8vLw0KDQoJLy9hZGRyZXNz57G75Z6L6L2sc3RyaW5nDQoJZnVuY3Rpb24gYWRkcmVzc1RvU3RyaW5nKGFkZHJlc3MgX2FkZHIpIHB1YmxpYyBwdXJlIHJldHVybnMoc3RyaW5nKSB7DQoJCWJ5dGVzMzIgdmFsdWUgPSBieXRlczMyKHVpbnQyNTYoX2FkZHIpKTsNCgkJYnl0ZXMgbWVtb3J5IGFscGhhYmV0ID0gIjAxMjM0NTY3ODlhYmNkZWYiOw0KDQoJCWJ5dGVzIG1lbW9yeSBzdHIgPSBuZXcgYnl0ZXMoNTEpOw0KCQlzdHJbMF0gPSAiMCI7DQoJCXN0clsxXSA9ICJ4IjsNCgkJZm9yICh1aW50IGkgPSAwOyBpIDwgMjA7IGkrKykgew0KCQkJc3RyWzIraSoyXSA9IGFscGhhYmV0W3VpbnQodWludDgodmFsdWVbaSArIDEyXSA+PiA0KSldOw0KCQkJc3RyWzMraSoyXSA9IGFscGhhYmV0W3VpbnQodWludDgodmFsdWVbaSArIDEyXSAmIDB4MGYpKV07DQoJCX0NCgkJcmV0dXJuIHN0cmluZyhzdHIpOw0KCX0NCg0KCS8v6L+U5Zue5omA5pyJ55qE54mI5pys5YiX6KGoDQoJZnVuY3Rpb24gZ2V0VmVyc2lvbnMoKSB2aWV3IHJldHVybnMgKHN0cmluZyBtZW1vcnkgcmVzdWx0KXsNCgkJcmVzdWx0PSJ7IjsNCgkJZm9yKHVpbnQgaSA9IDA7IGkgPCB2ZXJzaW9uTGlzdC5sZW5ndGg7IGkrKykgew0KCQkJcmVzdWx0ID0gcmVzdWx0LnRvU2xpY2UoKS5jb25jYXQodmVyc2lvbkxpc3RbaV0udG9TbGljZSgpKTsNCgkJCXJlc3VsdCA9IHJlc3VsdC50b1NsaWNlKCkuY29uY2F0KCI6Ii50b1NsaWNlKCkpOw0KCQkJcmVzdWx0ID0gcmVzdWx0LnRvU2xpY2UoKS5jb25jYXQoYWRkcmVzc1RvU3RyaW5nKF92ZXJzaW9uc1t2ZXJzaW9uTGlzdFtpXV0pLnRvU2xpY2UoKSk7DQoJCQlpZihpICE9ICh2ZXJzaW9uTGlzdC5sZW5ndGgtMSkpIHsNCgkJCQlyZXN1bHQgPSByZXN1bHQudG9TbGljZSgpLmNvbmNhdCgiLCIudG9TbGljZSgpKTsNCgkJCX0NCgkJfQ0KCQlyZXN1bHQgPSByZXN1bHQudG9TbGljZSgpLmNvbmNhdCgifSIudG9TbGljZSgpKTsNCgl9DQoNCgkvLyDov5Tlm57lrp7njrDlnLDlnYANCglmdW5jdGlvbiBpbXBsZW1lbnRhdGlvbigpIHB1YmxpYyB2aWV3IHJldHVybnMgKGFkZHJlc3MpIHsNCgkJcmV0dXJuIF92ZXJzaW9uc1t2ZXJzaW9uXTsNCgl9DQoNCgkvLyDmm7TmlrDlrp7njrDlnLDlnYANCglmdW5jdGlvbiB1cGdyYWRlVG8oc3RyaW5nIG1lbW9yeSBfbmV3VmVyc2lvbiwgYWRkcmVzcyBfbmV3SW1wbGVtZW50YXRpb24pIHB1YmxpYyBvbmx5T3duZXIgew0KCQlyZXF1aXJlKGltcGxlbWVudGF0aW9uKCkgIT0gX25ld0ltcGxlbWVudGF0aW9uICYmIF9uZXdJbXBsZW1lbnRhdGlvbiAhPSBhZGRyZXNzKDApLCAiUHJveHk6IE9sZCBhZGRyZXNzIGlzIG5vdCBhbGxvd2VkIGFuZCBpbXBsZW1lbnRhdGlvbiBhZGRyZXNzIHNob3VsZCBub3QgYmUgMHgiKTsNCgkJcmVxdWlyZShBZGRyZXNzLmlzQ29udHJhY3QoX25ld0ltcGxlbWVudGF0aW9uKSwgIlByb3h5OiBDYW5ub3Qgc2V0IGEgcHJveHkgaW1wbGVtZW50YXRpb24gdG8gYSBub24tY29udHJhY3QgYWRkcmVzcyIpOw0KCQlyZXF1aXJlKGJ5dGVzKF9uZXdWZXJzaW9uKS5sZW5ndGggPiAwLCAiUHJveHk6IFZlcnNpb24gc2hvdWxkIG5vdCBiZSBlbXB0eSBzdHJpbmciKTsNCgkJdmVyc2lvbiA9IF9uZXdWZXJzaW9uOw0KCQlfdmVyc2lvbnNbdmVyc2lvbl0gPSBfbmV3SW1wbGVtZW50YXRpb247DQoJCXZlcnNpb25MaXN0LnB1c2goX25ld1ZlcnNpb24pOw0KCQllbWl0IFVwZ3JhZGVkKF9uZXdWZXJzaW9uLCBfbmV3SW1wbGVtZW50YXRpb24pOw0KCX0NCg0KCS8vIOiOt+WPlueJiOacrOWvueW6lOeahOmAu+i+keWQiOe6puWcsOWdgA0KCWZ1bmN0aW9uIGdldEltcGxGcm9tVmVyc2lvbihzdHJpbmcgIF92ZXJzaW9uKSBleHRlcm5hbCAgdmlldyBvbmx5T3duZXIgcmV0dXJucyhhZGRyZXNzKSB7DQoJCXJlcXVpcmUoYnl0ZXMoX3ZlcnNpb24pLmxlbmd0aCA+IDAsICJWZXJzaW9uIHNob3VsZCBub3QgYmUgZW1wdHkgc3RyaW5nIik7DQoJCXJldHVybiBfdmVyc2lvbnNbX3ZlcnNpb25dOw0KCX0NCg0KCS8vIGZhbGxiYWNrDQoJZnVuY3Rpb24gKCkgcGF5YWJsZSBleHRlcm5hbCB7DQoJCWFkZHJlc3MgX2ltcGwgPSBpbXBsZW1lbnRhdGlvbigpOw0KCQlyZXF1aXJlKF9pbXBsICE9IGFkZHJlc3MoMCksICJpbXBsZW1lbnRhdGlvbiBub3Qgc2V0Iik7DQoNCgkJLy8g5aeU5omY6LCD55So6L+U5Zue57uT5p6cDQoJCWFzc2VtYmx5IHsNCgkJCWxldCBwdHIgOj0gbWxvYWQoMHg0MCkNCgkJCWNhbGxkYXRhY29weShwdHIsIDAsIGNhbGxkYXRhc2l6ZSkNCgkJCWxldCByZXN1bHQgOj0gZGVsZWdhdGVjYWxsKGdhcywgX2ltcGwsIHB0ciwgY2FsbGRhdGFzaXplLCAwLCAwKQ0KCQkJbGV0IHNpemUgOj0gcmV0dXJuZGF0YXNpemUNCgkJCXJldHVybmRhdGFjb3B5KHB0ciwgMCwgc2l6ZSkNCg0KCQkJc3dpdGNoIHJlc3VsdA0KCQkJY2FzZSAwIHsgcmV2ZXJ0KHB0ciwgc2l6ZSkgfQ0KCQkJZGVmYXVsdCB7IHJldHVybihwdHIsIHNpemUpIH0NCgkJfQ0KCX0NCn0NCg==";
    public static final String BASE_STORAGE_SOURCE = "cHJhZ21hIHNvbGlkaXR5IF4wLjQuMjU7DQoNCmltcG9ydCAiLi9Pd25hYmxlLnNvbCI7DQoNCi8qKg0KICog54i25a2Y5YKo5ZCI57qmDQogKi8NCmNvbnRyYWN0IEJhc2VTdG9yYWdlIGlzIE93bmFibGUgew0KDQogICAgLy8g5YWl5Y+j5Zyw5Z2ADQogICAgYWRkcmVzcyBwdWJsaWMgcHJveHlBZGRyZXNzOw0KDQogICAgLy8vLy8vLy8vLy8vLy8vDQogICAgLy8vLyBFdmVudA0KICAgIC8vLy8vLy8vLy8vLy8vLw0KDQogICAgZXZlbnQgQ3JlYXRlUmVzdWx0KGludCBjb3VudCk7DQogICAgZXZlbnQgSW5zZXJ0UmVzdWx0KGludCBjb3VudCk7DQogICAgZXZlbnQgVXBkYXRlUmVzdWx0KGludCBjb3VudCk7DQogICAgZXZlbnQgUHV0UmVzdWx0KGludCBhY3Rpb24saW50IGNvdW50KTsNCiAgICBldmVudCBSZW1vdmVSZXN1bHQoaW50IGNvdW50KTsNCiAgICBldmVudCBTZXRQcm94eShhZGRyZXNzIG9wZXJhdG9yLCBhZGRyZXNzIHByb3h5KTsNCg0KICAgIC8vLy8vLy8vLy8vLy8vLw0KICAgIC8vLy8gTW9kaWZpZXINCiAgICAvLy8vLy8vLy8vLy8vLy8NCg0KICAgIC8vIOS7hemZkOWFpeWPo+WQiOe6puiwg+eUqA0KICAgIG1vZGlmaWVyIG9ubHlQcm94eSgpIHsNCiAgICAgICAgcmVxdWlyZShtc2cuc2VuZGVyID09IHByb3h5QWRkcmVzcywgIkJhc2VTdG9yYWdlOiBvbmx5IHByb3h5IGNhbiBjYWxsIik7DQogICAgICAgIF87DQogICAgfQ0KDQogICAgLy8vLy8vLy8vLy8vLy8vDQogICAgLy8vLyBGdW5jdGlvbnMNCiAgICAvLy8vLy8vLy8vLy8vLy8NCg0KICAgIC8vIOiuvue9ruWFpeWPow0KICAgIGZ1bmN0aW9uIHNldFByb3h5KGFkZHJlc3MgX3Byb3h5KSBleHRlcm5hbCBvbmx5T3duZXIgew0KICAgICAgICBwcm94eUFkZHJlc3MgPSBfcHJveHk7DQogICAgICAgIGVtaXQgU2V0UHJveHkobXNnLnNlbmRlciwgX3Byb3h5KTsNCiAgICB9DQoNCn0NCg==";

//    public static final String ADDRESS_SOURCE = "cHJhZ21hIHNvbGlkaXR5IF4wLjQuMjU7CgovKioKICog5qOA5p+l5Zyw5Z2A5piv5aSW6YOo6LSm5oi35Zyw5Z2A6L+Y5piv5ZCI57qm5Zyw5Z2ACiAqLwpsaWJyYXJ5IEFkZHJlc3MgewoKICAgIGZ1bmN0aW9uIGlzQ29udHJhY3QoYWRkcmVzcyBhY2NvdW50KSBpbnRlcm5hbCB2aWV3IHJldHVybnMgKGJvb2wpIHsKICAgICAgICB1aW50MjU2IHNpemU7CiAgICAgICAgYXNzZW1ibHkgeyBzaXplIDo9IGV4dGNvZGVzaXplKGFjY291bnQpIH0KICAgICAgICByZXR1cm4gc2l6ZSA+IDA7CiAgICB9Cn0K";
    public static final String OWNABLE_SOURCE = "cHJhZ21hIHNvbGlkaXR5IF4wLjQuMjU7DQoNCmNvbnRyYWN0IE93bmFibGUgew0KICAgIGFkZHJlc3MgcHJpdmF0ZSBfb3duZXI7DQoNCiAgICBldmVudCBPd25lcnNoaXBUcmFuc2ZlcnJlZChhZGRyZXNzICBwcmV2aW91c093bmVyLCBhZGRyZXNzICBuZXdPd25lcik7DQoNCiAgICAvKioNCiAgICAgKiBAZGV2IFRoZSBPd25hYmxlIGNvbnN0cnVjdG9yIHNldHMgdGhlIG9yaWdpbmFsIGBvd25lcmAgb2YgdGhlIGNvbnRyYWN0IHRvIHRoZSBzZW5kZXINCiAgICAgKiBhY2NvdW50Lg0KICAgICAqLw0KICAgIGNvbnN0cnVjdG9yICgpIGludGVybmFsIHsNCiAgICAgICAgX293bmVyID0gbXNnLnNlbmRlcjsNCiAgICAgICAgZW1pdCBPd25lcnNoaXBUcmFuc2ZlcnJlZChhZGRyZXNzKDApLCBfb3duZXIpOw0KICAgIH0NCg0KICAgIC8qKg0KICAgICAqIEByZXR1cm4gdGhlIGFkZHJlc3Mgb2YgdGhlIG93bmVyLg0KICAgICAqLw0KICAgIGZ1bmN0aW9uIG93bmVyKCkgcHVibGljIHZpZXcgcmV0dXJucyAoYWRkcmVzcykgew0KICAgICAgICByZXR1cm4gX293bmVyOw0KICAgIH0NCg0KICAgIC8qKg0KICAgICAqIEBkZXYgVGhyb3dzIGlmIGNhbGxlZCBieSBhbnkgYWNjb3VudCBvdGhlciB0aGFuIHRoZSBvd25lci4NCiAgICAgKi8NCiAgICBtb2RpZmllciBvbmx5T3duZXIoKSB7DQogICAgICAgIHJlcXVpcmUoaXNPd25lcigpLCAiT3duYWJsZTogbm90IGF1dGhvcml6ZWQiKTsNCiAgICAgICAgXzsNCiAgICB9DQoNCiAgICAvKioNCiAgICAgKiBAcmV0dXJuIHRydWUgaWYgYG1zZy5zZW5kZXJgIGlzIHRoZSBvd25lciBvZiB0aGUgY29udHJhY3QuDQogICAgICovDQogICAgZnVuY3Rpb24gaXNPd25lcigpIHB1YmxpYyB2aWV3IHJldHVybnMgKGJvb2wpIHsNCiAgICAgICAgcmV0dXJuIG1zZy5zZW5kZXIgPT0gX293bmVyOw0KICAgIH0NCg0KICAgIC8qKg0KICAgICAqIEBkZXYgQWxsb3dzIHRoZSBjdXJyZW50IG93bmVyIHRvIHRyYW5zZmVyIGNvbnRyb2wgb2YgdGhlIGNvbnRyYWN0IHRvIGEgbmV3T3duZXIuDQogICAgICogQHBhcmFtIG5ld093bmVyIFRoZSBhZGRyZXNzIHRvIHRyYW5zZmVyIG93bmVyc2hpcCB0by4NCiAgICAgKi8NCiAgICBmdW5jdGlvbiB0cmFuc2Zlck93bmVyc2hpcChhZGRyZXNzIG5ld093bmVyKSBwdWJsaWMgb25seU93bmVyIHsNCiAgICAgICAgX3RyYW5zZmVyT3duZXJzaGlwKG5ld093bmVyKTsNCiAgICB9DQoNCiAgICAvKioNCiAgICAgKiBAZGV2IFRyYW5zZmVycyBjb250cm9sIG9mIHRoZSBjb250cmFjdCB0byBhIG5ld093bmVyLg0KICAgICAqIEBwYXJhbSBuZXdPd25lciBUaGUgYWRkcmVzcyB0byB0cmFuc2ZlciBvd25lcnNoaXAgdG8uDQogICAgICovDQogICAgZnVuY3Rpb24gX3RyYW5zZmVyT3duZXJzaGlwKGFkZHJlc3MgbmV3T3duZXIpIGludGVybmFsIHsNCiAgICAgICAgcmVxdWlyZShuZXdPd25lciAhPSBhZGRyZXNzKDApLCAiT3duYWJsZTogbmV3T3duZXIgbm90IGJlIHplcm8iKTsNCiAgICAgICAgZW1pdCBPd25lcnNoaXBUcmFuc2ZlcnJlZChfb3duZXIsIG5ld093bmVyKTsNCiAgICAgICAgX293bmVyID0gbmV3T3duZXI7DQogICAgfQ0KfQ0K";
    public static final String STRINGS_SOURCE = "LyoKICogQHRpdGxlIFN0cmluZyAmIHNsaWNlIHV0aWxpdHkgbGlicmFyeSBmb3IgU29saWRpdHkgY29udHJhY3RzLgogKiBAYXV0aG9yIE5pY2sgSm9obnNvbiA8YXJhY2huaWRAbm90ZG90Lm5ldD4KICoKICogQGRldiBGdW5jdGlvbmFsaXR5IGluIHRoaXMgbGlicmFyeSBpcyBsYXJnZWx5IGltcGxlbWVudGVkIHVzaW5nIGFuCiAqICAgICAgYWJzdHJhY3Rpb24gY2FsbGVkIGEgJ3NsaWNlJy4gQSBzbGljZSByZXByZXNlbnRzIGEgcGFydCBvZiBhIHN0cmluZyAtCiAqICAgICAgYW55dGhpbmcgZnJvbSB0aGUgZW50aXJlIHN0cmluZyB0byBhIHNpbmdsZSBjaGFyYWN0ZXIsIG9yIGV2ZW4gbm8KICogICAgICBjaGFyYWN0ZXJzIGF0IGFsbCAoYSAwLWxlbmd0aCBzbGljZSkuIFNpbmNlIGEgc2xpY2Ugb25seSBoYXMgdG8gc3BlY2lmeQogKiAgICAgIGFuIG9mZnNldCBhbmQgYSBsZW5ndGgsIGNvcHlpbmcgYW5kIG1hbmlwdWxhdGluZyBzbGljZXMgaXMgYSBsb3QgbGVzcwogKiAgICAgIGV4cGVuc2l2ZSB0aGFuIGNvcHlpbmcgYW5kIG1hbmlwdWxhdGluZyB0aGUgc3RyaW5ncyB0aGV5IHJlZmVyZW5jZS4KICoKICogICAgICBUbyBmdXJ0aGVyIHJlZHVjZSBnYXMgY29zdHMsIG1vc3QgZnVuY3Rpb25zIG9uIHNsaWNlIHRoYXQgbmVlZCB0byByZXR1cm4KICogICAgICBhIHNsaWNlIG1vZGlmeSB0aGUgb3JpZ2luYWwgb25lIGluc3RlYWQgb2YgYWxsb2NhdGluZyBhIG5ldyBvbmU7IGZvcgogKiAgICAgIGluc3RhbmNlLCBgcy5zcGxpdCgiLiIpYCB3aWxsIHJldHVybiB0aGUgdGV4dCB1cCB0byB0aGUgZmlyc3QgJy4nLAogKiAgICAgIG1vZGlmeWluZyBzIHRvIG9ubHkgY29udGFpbiB0aGUgcmVtYWluZGVyIG9mIHRoZSBzdHJpbmcgYWZ0ZXIgdGhlICcuJy4KICogICAgICBJbiBzaXR1YXRpb25zIHdoZXJlIHlvdSBkbyBub3Qgd2FudCB0byBtb2RpZnkgdGhlIG9yaWdpbmFsIHNsaWNlLCB5b3UKICogICAgICBjYW4gbWFrZSBhIGNvcHkgZmlyc3Qgd2l0aCBgLmNvcHkoKWAsIGZvciBleGFtcGxlOgogKiAgICAgIGBzLmNvcHkoKS5zcGxpdCgiLiIpYC4gVHJ5IGFuZCBhdm9pZCB1c2luZyB0aGlzIGlkaW9tIGluIGxvb3BzOyBzaW5jZQogKiAgICAgIFNvbGlkaXR5IGhhcyBubyBtZW1vcnkgbWFuYWdlbWVudCwgaXQgd2lsbCByZXN1bHQgaW4gYWxsb2NhdGluZyBtYW55CiAqICAgICAgc2hvcnQtbGl2ZWQgc2xpY2VzIHRoYXQgYXJlIGxhdGVyIGRpc2NhcmRlZC4KICoKICogICAgICBGdW5jdGlvbnMgdGhhdCByZXR1cm4gdHdvIHNsaWNlcyBjb21lIGluIHR3byB2ZXJzaW9uczogYSBub24tYWxsb2NhdGluZwogKiAgICAgIHZlcnNpb24gdGhhdCB0YWtlcyB0aGUgc2Vjb25kIHNsaWNlIGFzIGFuIGFyZ3VtZW50LCBtb2RpZnlpbmcgaXQgaW4KICogICAgICBwbGFjZSwgYW5kIGFuIGFsbG9jYXRpbmcgdmVyc2lvbiB0aGF0IGFsbG9jYXRlcyBhbmQgcmV0dXJucyB0aGUgc2Vjb25kCiAqICAgICAgc2xpY2U7IHNlZSBgbmV4dFJ1bmVgIGZvciBleGFtcGxlLgogKgogKiAgICAgIEZ1bmN0aW9ucyB0aGF0IGhhdmUgdG8gY29weSBzdHJpbmcgZGF0YSB3aWxsIHJldHVybiBzdHJpbmdzIHJhdGhlciB0aGFuCiAqICAgICAgc2xpY2VzOyB0aGVzZSBjYW4gYmUgY2FzdCBiYWNrIHRvIHNsaWNlcyBmb3IgZnVydGhlciBwcm9jZXNzaW5nIGlmCiAqICAgICAgcmVxdWlyZWQuCiAqCiAqICAgICAgRm9yIGNvbnZlbmllbmNlLCBzb21lIGZ1bmN0aW9ucyBhcmUgcHJvdmlkZWQgd2l0aCBub24tbW9kaWZ5aW5nCiAqICAgICAgdmFyaWFudHMgdGhhdCBjcmVhdGUgYSBuZXcgc2xpY2UgYW5kIHJldHVybiBib3RoOyBmb3IgaW5zdGFuY2UsCiAqICAgICAgYHMuc3BsaXROZXcoJy4nKWAgbGVhdmVzIHMgdW5tb2RpZmllZCwgYW5kIHJldHVybnMgdHdvIHZhbHVlcwogKiAgICAgIGNvcnJlc3BvbmRpbmcgdG8gdGhlIGxlZnQgYW5kIHJpZ2h0IHBhcnRzIG9mIHRoZSBzdHJpbmcuCiAqLwoKcHJhZ21hIHNvbGlkaXR5IF4wLjQuMjU7CgpsaWJyYXJ5IFN0cmluZ3MgewogICAgc3RydWN0IHNsaWNlIHsKICAgICAgICB1aW50IF9sZW47CiAgICAgICAgdWludCBfcHRyOwogICAgfQoKICAgIGZ1bmN0aW9uIG1lbWNweSh1aW50IGRlc3QsIHVpbnQgc3JjLCB1aW50IGxlbikgcHJpdmF0ZSBwdXJlIHsKICAgICAgICAvLyBDb3B5IHdvcmQtbGVuZ3RoIGNodW5rcyB3aGlsZSBwb3NzaWJsZQogICAgICAgIGZvcig7IGxlbiA+PSAzMjsgbGVuIC09IDMyKSB7CiAgICAgICAgICAgIGFzc2VtYmx5IHsKICAgICAgICAgICAgICAgIG1zdG9yZShkZXN0LCBtbG9hZChzcmMpKQogICAgICAgICAgICB9CiAgICAgICAgICAgIGRlc3QgKz0gMzI7CiAgICAgICAgICAgIHNyYyArPSAzMjsKICAgICAgICB9CgogICAgICAgIC8vIENvcHkgcmVtYWluaW5nIGJ5dGVzCiAgICAgICAgdWludCBtYXNrID0gMjU2ICoqICgzMiAtIGxlbikgLSAxOwogICAgICAgIGFzc2VtYmx5IHsKICAgICAgICAgICAgbGV0IHNyY3BhcnQgOj0gYW5kKG1sb2FkKHNyYyksIG5vdChtYXNrKSkKICAgICAgICAgICAgbGV0IGRlc3RwYXJ0IDo9IGFuZChtbG9hZChkZXN0KSwgbWFzaykKICAgICAgICAgICAgbXN0b3JlKGRlc3QsIG9yKGRlc3RwYXJ0LCBzcmNwYXJ0KSkKICAgICAgICB9CiAgICB9CgogICAgLyoKICAgICAqIEBkZXYgUmV0dXJucyBhIHNsaWNlIGNvbnRhaW5pbmcgdGhlIGVudGlyZSBzdHJpbmcuCiAgICAgKiBAcGFyYW0gc2VsZiBUaGUgc3RyaW5nIHRvIG1ha2UgYSBzbGljZSBmcm9tLgogICAgICogQHJldHVybiBBIG5ld2x5IGFsbG9jYXRlZCBzbGljZSBjb250YWluaW5nIHRoZSBlbnRpcmUgc3RyaW5nLgogICAgICovCiAgICBmdW5jdGlvbiB0b1NsaWNlKHN0cmluZyBtZW1vcnkgc2VsZikgaW50ZXJuYWwgcHVyZSByZXR1cm5zIChzbGljZSBtZW1vcnkpIHsKICAgICAgICB1aW50IHB0cjsKICAgICAgICBhc3NlbWJseSB7CiAgICAgICAgICAgIHB0ciA6PSBhZGQoc2VsZiwgMHgyMCkKICAgICAgICB9CiAgICAgICAgcmV0dXJuIHNsaWNlKGJ5dGVzKHNlbGYpLmxlbmd0aCwgcHRyKTsKICAgIH0KCiAgICAvKgogICAgICogQGRldiBSZXR1cm5zIHRoZSBsZW5ndGggb2YgYSBudWxsLXRlcm1pbmF0ZWQgYnl0ZXMzMiBzdHJpbmcuCiAgICAgKiBAcGFyYW0gc2VsZiBUaGUgdmFsdWUgdG8gZmluZCB0aGUgbGVuZ3RoIG9mLgogICAgICogQHJldHVybiBUaGUgbGVuZ3RoIG9mIHRoZSBzdHJpbmcsIGZyb20gMCB0byAzMi4KICAgICAqLwogICAgZnVuY3Rpb24gbGVuKGJ5dGVzMzIgc2VsZikgaW50ZXJuYWwgcHVyZSByZXR1cm5zICh1aW50KSB7CiAgICAgICAgdWludCByZXQ7CiAgICAgICAgaWYgKHNlbGYgPT0gMCkKICAgICAgICAgICAgcmV0dXJuIDA7CiAgICAgICAgaWYgKHNlbGYgJiAweGZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmID09IDApIHsKICAgICAgICAgICAgcmV0ICs9IDE2OwogICAgICAgICAgICBzZWxmID0gYnl0ZXMzMih1aW50KHNlbGYpIC8gMHgxMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDApOwogICAgICAgIH0KICAgICAgICBpZiAoc2VsZiAmIDB4ZmZmZmZmZmZmZmZmZmZmZiA9PSAwKSB7CiAgICAgICAgICAgIHJldCArPSA4OwogICAgICAgICAgICBzZWxmID0gYnl0ZXMzMih1aW50KHNlbGYpIC8gMHgxMDAwMDAwMDAwMDAwMDAwMCk7CiAgICAgICAgfQogICAgICAgIGlmIChzZWxmICYgMHhmZmZmZmZmZiA9PSAwKSB7CiAgICAgICAgICAgIHJldCArPSA0OwogICAgICAgICAgICBzZWxmID0gYnl0ZXMzMih1aW50KHNlbGYpIC8gMHgxMDAwMDAwMDApOwogICAgICAgIH0KICAgICAgICBpZiAoc2VsZiAmIDB4ZmZmZiA9PSAwKSB7CiAgICAgICAgICAgIHJldCArPSAyOwogICAgICAgICAgICBzZWxmID0gYnl0ZXMzMih1aW50KHNlbGYpIC8gMHgxMDAwMCk7CiAgICAgICAgfQogICAgICAgIGlmIChzZWxmICYgMHhmZiA9PSAwKSB7CiAgICAgICAgICAgIHJldCArPSAxOwogICAgICAgIH0KICAgICAgICByZXR1cm4gMzIgLSByZXQ7CiAgICB9CgogICAgLyoKICAgICAqIEBkZXYgUmV0dXJucyBhIHNsaWNlIGNvbnRhaW5pbmcgdGhlIGVudGlyZSBieXRlczMyLCBpbnRlcnByZXRlZCBhcyBhCiAgICAgKiAgICAgIG51bGwtdGVybWluYXRlZCB1dGYtOCBzdHJpbmcuCiAgICAgKiBAcGFyYW0gc2VsZiBUaGUgYnl0ZXMzMiB2YWx1ZSB0byBjb252ZXJ0IHRvIGEgc2xpY2UuCiAgICAgKiBAcmV0dXJuIEEgbmV3IHNsaWNlIGNvbnRhaW5pbmcgdGhlIHZhbHVlIG9mIHRoZSBpbnB1dCBhcmd1bWVudCB1cCB0byB0aGUKICAgICAqICAgICAgICAgZmlyc3QgbnVsbC4KICAgICAqLwogICAgZnVuY3Rpb24gdG9TbGljZUIzMihieXRlczMyIHNlbGYpIGludGVybmFsIHB1cmUgcmV0dXJucyAoc2xpY2UgbWVtb3J5IHJldCkgewogICAgICAgIC8vIEFsbG9jYXRlIHNwYWNlIGZvciBgc2VsZmAgaW4gbWVtb3J5LCBjb3B5IGl0IHRoZXJlLCBhbmQgcG9pbnQgcmV0IGF0IGl0CiAgICAgICAgYXNzZW1ibHkgewogICAgICAgICAgICBsZXQgcHRyIDo9IG1sb2FkKDB4NDApCiAgICAgICAgICAgIG1zdG9yZSgweDQwLCBhZGQocHRyLCAweDIwKSkKICAgICAgICAgICAgbXN0b3JlKHB0ciwgc2VsZikKICAgICAgICAgICAgbXN0b3JlKGFkZChyZXQsIDB4MjApLCBwdHIpCiAgICAgICAgfQogICAgICAgIHJldC5fbGVuID0gbGVuKHNlbGYpOwogICAgfQoKICAgIC8qCiAgICAgKiBAZGV2IFJldHVybnMgYSBuZXcgc2xpY2UgY29udGFpbmluZyB0aGUgc2FtZSBkYXRhIGFzIHRoZSBjdXJyZW50IHNsaWNlLgogICAgICogQHBhcmFtIHNlbGYgVGhlIHNsaWNlIHRvIGNvcHkuCiAgICAgKiBAcmV0dXJuIEEgbmV3IHNsaWNlIGNvbnRhaW5pbmcgdGhlIHNhbWUgZGF0YSBhcyBgc2VsZmAuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGNvcHkoc2xpY2UgbWVtb3J5IHNlbGYpIGludGVybmFsIHB1cmUgcmV0dXJucyAoc2xpY2UgbWVtb3J5KSB7CiAgICAgICAgcmV0dXJuIHNsaWNlKHNlbGYuX2xlbiwgc2VsZi5fcHRyKTsKICAgIH0KCiAgICAvKgogICAgICogQGRldiBDb3BpZXMgYSBzbGljZSB0byBhIG5ldyBzdHJpbmcuCiAgICAgKiBAcGFyYW0gc2VsZiBUaGUgc2xpY2UgdG8gY29weS4KICAgICAqIEByZXR1cm4gQSBuZXdseSBhbGxvY2F0ZWQgc3RyaW5nIGNvbnRhaW5pbmcgdGhlIHNsaWNlJ3MgdGV4dC4KICAgICAqLwogICAgZnVuY3Rpb24gdG9TdHJpbmcoc2xpY2UgbWVtb3J5IHNlbGYpIGludGVybmFsIHB1cmUgcmV0dXJucyAoc3RyaW5nIG1lbW9yeSkgewogICAgICAgIHN0cmluZyBtZW1vcnkgcmV0ID0gbmV3IHN0cmluZyhzZWxmLl9sZW4pOwogICAgICAgIHVpbnQgcmV0cHRyOwogICAgICAgIGFzc2VtYmx5IHsgcmV0cHRyIDo9IGFkZChyZXQsIDMyKSB9CgogICAgICAgIG1lbWNweShyZXRwdHIsIHNlbGYuX3B0ciwgc2VsZi5fbGVuKTsKICAgICAgICByZXR1cm4gcmV0OwogICAgfQoKICAgIC8qCiAgICAgKiBAZGV2IFJldHVybnMgdGhlIGxlbmd0aCBpbiBydW5lcyBvZiB0aGUgc2xpY2UuIE5vdGUgdGhhdCB0aGlzIG9wZXJhdGlvbgogICAgICogICAgICB0YWtlcyB0aW1lIHByb3BvcnRpb25hbCB0byB0aGUgbGVuZ3RoIG9mIHRoZSBzbGljZTsgYXZvaWQgdXNpbmcgaXQKICAgICAqICAgICAgaW4gbG9vcHMsIGFuZCBjYWxsIGBzbGljZS5lbXB0eSgpYCBpZiB5b3Ugb25seSBuZWVkIHRvIGtub3cgd2hldGhlcgogICAgICogICAgICB0aGUgc2xpY2UgaXMgZW1wdHkgb3Igbm90LgogICAgICogQHBhcmFtIHNlbGYgVGhlIHNsaWNlIHRvIG9wZXJhdGUgb24uCiAgICAgKiBAcmV0dXJuIFRoZSBsZW5ndGggb2YgdGhlIHNsaWNlIGluIHJ1bmVzLgogICAgICovCiAgICBmdW5jdGlvbiBsZW4oc2xpY2UgbWVtb3J5IHNlbGYpIGludGVybmFsIHB1cmUgcmV0dXJucyAodWludCBsKSB7CiAgICAgICAgLy8gU3RhcnRpbmcgYXQgcHRyLTMxIG1lYW5zIHRoZSBMU0Igd2lsbCBiZSB0aGUgYnl0ZSB3ZSBjYXJlIGFib3V0CiAgICAgICAgdWludCBwdHIgPSBzZWxmLl9wdHIgLSAzMTsKICAgICAgICB1aW50IGVuZCA9IHB0ciArIHNlbGYuX2xlbjsKICAgICAgICBmb3IgKGwgPSAwOyBwdHIgPCBlbmQ7IGwrKykgewogICAgICAgICAgICB1aW50OCBiOwogICAgICAgICAgICBhc3NlbWJseSB7IGIgOj0gYW5kKG1sb2FkKHB0ciksIDB4RkYpIH0KICAgICAgICAgICAgaWYgKGIgPCAweDgwKSB7CiAgICAgICAgICAgICAgICBwdHIgKz0gMTsKICAgICAgICAgICAgfSBlbHNlIGlmKGIgPCAweEUwKSB7CiAgICAgICAgICAgICAgICBwdHIgKz0gMjsKICAgICAgICAgICAgfSBlbHNlIGlmKGIgPCAweEYwKSB7CiAgICAgICAgICAgICAgICBwdHIgKz0gMzsKICAgICAgICAgICAgfSBlbHNlIGlmKGIgPCAweEY4KSB7CiAgICAgICAgICAgICAgICBwdHIgKz0gNDsKICAgICAgICAgICAgfSBlbHNlIGlmKGIgPCAweEZDKSB7CiAgICAgICAgICAgICAgICBwdHIgKz0gNTsKICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICAgIHB0ciArPSA2OwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgfQoKICAgIC8qCiAgICAgKiBAZGV2IFJldHVybnMgdHJ1ZSBpZiB0aGUgc2xpY2UgaXMgZW1wdHkgKGhhcyBhIGxlbmd0aCBvZiAwKS4KICAgICAqIEBwYXJhbSBzZWxmIFRoZSBzbGljZSB0byBvcGVyYXRlIG9uLgogICAgICogQHJldHVybiBUcnVlIGlmIHRoZSBzbGljZSBpcyBlbXB0eSwgRmFsc2Ugb3RoZXJ3aXNlLgogICAgICovCiAgICBmdW5jdGlvbiBlbXB0eShzbGljZSBtZW1vcnkgc2VsZikgaW50ZXJuYWwgcHVyZSByZXR1cm5zIChib29sKSB7CiAgICAgICAgcmV0dXJuIHNlbGYuX2xlbiA9PSAwOwogICAgfQoKICAgIC8qCiAgICAgKiBAZGV2IFJldHVybnMgYSBwb3NpdGl2ZSBudW1iZXIgaWYgYG90aGVyYCBjb21lcyBsZXhpY29ncmFwaGljYWxseSBhZnRlcgogICAgICogICAgICBgc2VsZmAsIGEgbmVnYXRpdmUgbnVtYmVyIGlmIGl0IGNvbWVzIGJlZm9yZSwgb3IgemVybyBpZiB0aGUKICAgICAqICAgICAgY29udGVudHMgb2YgdGhlIHR3byBzbGljZXMgYXJlIGVxdWFsLiBDb21wYXJpc29uIGlzIGRvbmUgcGVyLXJ1bmUsCiAgICAgKiAgICAgIG9uIHVuaWNvZGUgY29kZXBvaW50cy4KICAgICAqIEBwYXJhbSBzZWxmIFRoZSBmaXJzdCBzbGljZSB0byBjb21wYXJlLgogICAgICogQHBhcmFtIG90aGVyIFRoZSBzZWNvbmQgc2xpY2UgdG8gY29tcGFyZS4KICAgICAqIEByZXR1cm4gVGhlIHJlc3VsdCBvZiB0aGUgY29tcGFyaXNvbi4KICAgICAqLwogICAgZnVuY3Rpb24gY29tcGFyZShzbGljZSBtZW1vcnkgc2VsZiwgc2xpY2UgbWVtb3J5IG90aGVyKSBpbnRlcm5hbCBwdXJlIHJldHVybnMgKGludCkgewogICAgICAgIHVpbnQgc2hvcnRlc3QgPSBzZWxmLl9sZW47CiAgICAgICAgaWYgKG90aGVyLl9sZW4gPCBzZWxmLl9sZW4pCiAgICAgICAgICAgIHNob3J0ZXN0ID0gb3RoZXIuX2xlbjsKCiAgICAgICAgdWludCBzZWxmcHRyID0gc2VsZi5fcHRyOwogICAgICAgIHVpbnQgb3RoZXJwdHIgPSBvdGhlci5fcHRyOwogICAgICAgIGZvciAodWludCBpZHggPSAwOyBpZHggPCBzaG9ydGVzdDsgaWR4ICs9IDMyKSB7CiAgICAgICAgICAgIHVpbnQgYTsKICAgICAgICAgICAgdWludCBiOwogICAgICAgICAgICBhc3NlbWJseSB7CiAgICAgICAgICAgICAgICBhIDo9IG1sb2FkKHNlbGZwdHIpCiAgICAgICAgICAgICAgICBiIDo9IG1sb2FkKG90aGVycHRyKQogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmIChhICE9IGIpIHsKICAgICAgICAgICAgICAgIC8vIE1hc2sgb3V0IGlycmVsZXZhbnQgYnl0ZXMgYW5kIGNoZWNrIGFnYWluCiAgICAgICAgICAgICAgICB1aW50MjU2IG1hc2sgPSB1aW50MjU2KC0xKTsgLy8gMHhmZmZmLi4uCiAgICAgICAgICAgICAgICBpZihzaG9ydGVzdCA8IDMyKSB7CiAgICAgICAgICAgICAgICAgIG1hc2sgPSB+KDIgKiogKDggKiAoMzIgLSBzaG9ydGVzdCArIGlkeCkpIC0gMSk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB1aW50MjU2IGRpZmYgPSAoYSAmIG1hc2spIC0gKGIgJiBtYXNrKTsKICAgICAgICAgICAgICAgIGlmIChkaWZmICE9IDApCiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIGludChkaWZmKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBzZWxmcHRyICs9IDMyOwogICAgICAgICAgICBvdGhlcnB0ciArPSAzMjsKICAgICAgICB9CiAgICAgICAgcmV0dXJuIGludChzZWxmLl9sZW4pIC0gaW50KG90aGVyLl9sZW4pOwogICAgfQoKICAgIC8qCiAgICAgKiBAZGV2IFJldHVybnMgdHJ1ZSBpZiB0aGUgdHdvIHNsaWNlcyBjb250YWluIHRoZSBzYW1lIHRleHQuCiAgICAgKiBAcGFyYW0gc2VsZiBUaGUgZmlyc3Qgc2xpY2UgdG8gY29tcGFyZS4KICAgICAqIEBwYXJhbSBzZWxmIFRoZSBzZWNvbmQgc2xpY2UgdG8gY29tcGFyZS4KICAgICAqIEByZXR1cm4gVHJ1ZSBpZiB0aGUgc2xpY2VzIGFyZSBlcXVhbCwgZmFsc2Ugb3RoZXJ3aXNlLgogICAgICovCiAgICBmdW5jdGlvbiBlcXVhbHMoc2xpY2UgbWVtb3J5IHNlbGYsIHNsaWNlIG1lbW9yeSBvdGhlcikgaW50ZXJuYWwgcHVyZSByZXR1cm5zIChib29sKSB7CiAgICAgICAgcmV0dXJuIGNvbXBhcmUoc2VsZiwgb3RoZXIpID09IDA7CiAgICB9CgogICAgLyoKICAgICAqIEBkZXYgRXh0cmFjdHMgdGhlIGZpcnN0IHJ1bmUgaW4gdGhlIHNsaWNlIGludG8gYHJ1bmVgLCBhZHZhbmNpbmcgdGhlCiAgICAgKiAgICAgIHNsaWNlIHRvIHBvaW50IHRvIHRoZSBuZXh0IHJ1bmUgYW5kIHJldHVybmluZyBgc2VsZmAuCiAgICAgKiBAcGFyYW0gc2VsZiBUaGUgc2xpY2UgdG8gb3BlcmF0ZSBvbi4KICAgICAqIEBwYXJhbSBydW5lIFRoZSBzbGljZSB0aGF0IHdpbGwgY29udGFpbiB0aGUgZmlyc3QgcnVuZS4KICAgICAqIEByZXR1cm4gYHJ1bmVgLgogICAgICovCiAgICBmdW5jdGlvbiBuZXh0UnVuZShzbGljZSBtZW1vcnkgc2VsZiwgc2xpY2UgbWVtb3J5IHJ1bmUpIGludGVybmFsIHB1cmUgcmV0dXJucyAoc2xpY2UgbWVtb3J5KSB7CiAgICAgICAgcnVuZS5fcHRyID0gc2VsZi5fcHRyOwoKICAgICAgICBpZiAoc2VsZi5fbGVuID09IDApIHsKICAgICAgICAgICAgcnVuZS5fbGVuID0gMDsKICAgICAgICAgICAgcmV0dXJuIHJ1bmU7CiAgICAgICAgfQoKICAgICAgICB1aW50IGw7CiAgICAgICAgdWludCBiOwogICAgICAgIC8vIExvYWQgdGhlIGZpcnN0IGJ5dGUgb2YgdGhlIHJ1bmUgaW50byB0aGUgTFNCcyBvZiBiCiAgICAgICAgYXNzZW1ibHkgeyBiIDo9IGFuZChtbG9hZChzdWIobWxvYWQoYWRkKHNlbGYsIDMyKSksIDMxKSksIDB4RkYpIH0KICAgICAgICBpZiAoYiA8IDB4ODApIHsKICAgICAgICAgICAgbCA9IDE7CiAgICAgICAgfSBlbHNlIGlmKGIgPCAweEUwKSB7CiAgICAgICAgICAgIGwgPSAyOwogICAgICAgIH0gZWxzZSBpZihiIDwgMHhGMCkgewogICAgICAgICAgICBsID0gMzsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgICBsID0gNDsKICAgICAgICB9CgogICAgICAgIC8vIENoZWNrIGZvciB0cnVuY2F0ZWQgY29kZXBvaW50cwogICAgICAgIGlmIChsID4gc2VsZi5fbGVuKSB7CiAgICAgICAgICAgIHJ1bmUuX2xlbiA9IHNlbGYuX2xlbjsKICAgICAgICAgICAgc2VsZi5fcHRyICs9IHNlbGYuX2xlbjsKICAgICAgICAgICAgc2VsZi5fbGVuID0gMDsKICAgICAgICAgICAgcmV0dXJuIHJ1bmU7CiAgICAgICAgfQoKICAgICAgICBzZWxmLl9wdHIgKz0gbDsKICAgICAgICBzZWxmLl9sZW4gLT0gbDsKICAgICAgICBydW5lLl9sZW4gPSBsOwogICAgICAgIHJldHVybiBydW5lOwogICAgfQoKICAgIC8qCiAgICAgKiBAZGV2IFJldHVybnMgdGhlIGZpcnN0IHJ1bmUgaW4gdGhlIHNsaWNlLCBhZHZhbmNpbmcgdGhlIHNsaWNlIHRvIHBvaW50CiAgICAgKiAgICAgIHRvIHRoZSBuZXh0IHJ1bmUuCiAgICAgKiBAcGFyYW0gc2VsZiBUaGUgc2xpY2UgdG8gb3BlcmF0ZSBvbi4KICAgICAqIEByZXR1cm4gQSBzbGljZSBjb250YWluaW5nIG9ubHkgdGhlIGZpcnN0IHJ1bmUgZnJvbSBgc2VsZmAuCiAgICAgKi8KICAgIGZ1bmN0aW9uIG5leHRSdW5lKHNsaWNlIG1lbW9yeSBzZWxmKSBpbnRlcm5hbCBwdXJlIHJldHVybnMgKHNsaWNlIG1lbW9yeSByZXQpIHsKICAgICAgICBuZXh0UnVuZShzZWxmLCByZXQpOwogICAgfQoKICAgIC8qCiAgICAgKiBAZGV2IFJldHVybnMgdGhlIG51bWJlciBvZiB0aGUgZmlyc3QgY29kZXBvaW50IGluIHRoZSBzbGljZS4KICAgICAqIEBwYXJhbSBzZWxmIFRoZSBzbGljZSB0byBvcGVyYXRlIG9uLgogICAgICogQHJldHVybiBUaGUgbnVtYmVyIG9mIHRoZSBmaXJzdCBjb2RlcG9pbnQgaW4gdGhlIHNsaWNlLgogICAgICovCiAgICBmdW5jdGlvbiBvcmQoc2xpY2UgbWVtb3J5IHNlbGYpIGludGVybmFsIHB1cmUgcmV0dXJucyAodWludCByZXQpIHsKICAgICAgICBpZiAoc2VsZi5fbGVuID09IDApIHsKICAgICAgICAgICAgcmV0dXJuIDA7CiAgICAgICAgfQoKICAgICAgICB1aW50IHdvcmQ7CiAgICAgICAgdWludCBsZW5ndGg7CiAgICAgICAgdWludCBkaXZpc29yID0gMiAqKiAyNDg7CgogICAgICAgIC8vIExvYWQgdGhlIHJ1bmUgaW50byB0aGUgTVNCcyBvZiBiCiAgICAgICAgYXNzZW1ibHkgeyB3b3JkOj0gbWxvYWQobWxvYWQoYWRkKHNlbGYsIDMyKSkpIH0KICAgICAgICB1aW50IGIgPSB3b3JkIC8gZGl2aXNvcjsKICAgICAgICBpZiAoYiA8IDB4ODApIHsKICAgICAgICAgICAgcmV0ID0gYjsKICAgICAgICAgICAgbGVuZ3RoID0gMTsKICAgICAgICB9IGVsc2UgaWYoYiA8IDB4RTApIHsKICAgICAgICAgICAgcmV0ID0gYiAmIDB4MUY7CiAgICAgICAgICAgIGxlbmd0aCA9IDI7CiAgICAgICAgfSBlbHNlIGlmKGIgPCAweEYwKSB7CiAgICAgICAgICAgIHJldCA9IGIgJiAweDBGOwogICAgICAgICAgICBsZW5ndGggPSAzOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIHJldCA9IGIgJiAweDA3OwogICAgICAgICAgICBsZW5ndGggPSA0OwogICAgICAgIH0KCiAgICAgICAgLy8gQ2hlY2sgZm9yIHRydW5jYXRlZCBjb2RlcG9pbnRzCiAgICAgICAgaWYgKGxlbmd0aCA+IHNlbGYuX2xlbikgewogICAgICAgICAgICByZXR1cm4gMDsKICAgICAgICB9CgogICAgICAgIGZvciAodWludCBpID0gMTsgaSA8IGxlbmd0aDsgaSsrKSB7CiAgICAgICAgICAgIGRpdmlzb3IgPSBkaXZpc29yIC8gMjU2OwogICAgICAgICAgICBiID0gKHdvcmQgLyBkaXZpc29yKSAmIDB4RkY7CiAgICAgICAgICAgIGlmIChiICYgMHhDMCAhPSAweDgwKSB7CiAgICAgICAgICAgICAgICAvLyBJbnZhbGlkIFVURi04IHNlcXVlbmNlCiAgICAgICAgICAgICAgICByZXR1cm4gMDsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXQgPSAocmV0ICogNjQpIHwgKGIgJiAweDNGKTsKICAgICAgICB9CgogICAgICAgIHJldHVybiByZXQ7CiAgICB9CgogICAgLyoKICAgICAqIEBkZXYgUmV0dXJucyB0aGUga2VjY2FrLTI1NiBoYXNoIG9mIHRoZSBzbGljZS4KICAgICAqIEBwYXJhbSBzZWxmIFRoZSBzbGljZSB0byBoYXNoLgogICAgICogQHJldHVybiBUaGUgaGFzaCBvZiB0aGUgc2xpY2UuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGtlY2NhayhzbGljZSBtZW1vcnkgc2VsZikgaW50ZXJuYWwgcHVyZSByZXR1cm5zIChieXRlczMyIHJldCkgewogICAgICAgIGFzc2VtYmx5IHsKICAgICAgICAgICAgcmV0IDo9IGtlY2NhazI1NihtbG9hZChhZGQoc2VsZiwgMzIpKSwgbWxvYWQoc2VsZikpCiAgICAgICAgfQogICAgfQoKICAgIC8qCiAgICAgKiBAZGV2IFJldHVybnMgdHJ1ZSBpZiBgc2VsZmAgc3RhcnRzIHdpdGggYG5lZWRsZWAuCiAgICAgKiBAcGFyYW0gc2VsZiBUaGUgc2xpY2UgdG8gb3BlcmF0ZSBvbi4KICAgICAqIEBwYXJhbSBuZWVkbGUgVGhlIHNsaWNlIHRvIHNlYXJjaCBmb3IuCiAgICAgKiBAcmV0dXJuIFRydWUgaWYgdGhlIHNsaWNlIHN0YXJ0cyB3aXRoIHRoZSBwcm92aWRlZCB0ZXh0LCBmYWxzZSBvdGhlcndpc2UuCiAgICAgKi8KICAgIGZ1bmN0aW9uIHN0YXJ0c1dpdGgoc2xpY2UgbWVtb3J5IHNlbGYsIHNsaWNlIG1lbW9yeSBuZWVkbGUpIGludGVybmFsIHB1cmUgcmV0dXJucyAoYm9vbCkgewogICAgICAgIGlmIChzZWxmLl9sZW4gPCBuZWVkbGUuX2xlbikgewogICAgICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgICAgfQoKICAgICAgICBpZiAoc2VsZi5fcHRyID09IG5lZWRsZS5fcHRyKSB7CiAgICAgICAgICAgIHJldHVybiB0cnVlOwogICAgICAgIH0KCiAgICAgICAgYm9vbCBlcXVhbDsKICAgICAgICBhc3NlbWJseSB7CiAgICAgICAgICAgIGxldCBsZW5ndGggOj0gbWxvYWQobmVlZGxlKQogICAgICAgICAgICBsZXQgc2VsZnB0ciA6PSBtbG9hZChhZGQoc2VsZiwgMHgyMCkpCiAgICAgICAgICAgIGxldCBuZWVkbGVwdHIgOj0gbWxvYWQoYWRkKG5lZWRsZSwgMHgyMCkpCiAgICAgICAgICAgIGVxdWFsIDo9IGVxKGtlY2NhazI1NihzZWxmcHRyLCBsZW5ndGgpLCBrZWNjYWsyNTYobmVlZGxlcHRyLCBsZW5ndGgpKQogICAgICAgIH0KICAgICAgICByZXR1cm4gZXF1YWw7CiAgICB9CgogICAgLyoKICAgICAqIEBkZXYgSWYgYHNlbGZgIHN0YXJ0cyB3aXRoIGBuZWVkbGVgLCBgbmVlZGxlYCBpcyByZW1vdmVkIGZyb20gdGhlCiAgICAgKiAgICAgIGJlZ2lubmluZyBvZiBgc2VsZmAuIE90aGVyd2lzZSwgYHNlbGZgIGlzIHVubW9kaWZpZWQuCiAgICAgKiBAcGFyYW0gc2VsZiBUaGUgc2xpY2UgdG8gb3BlcmF0ZSBvbi4KICAgICAqIEBwYXJhbSBuZWVkbGUgVGhlIHNsaWNlIHRvIHNlYXJjaCBmb3IuCiAgICAgKiBAcmV0dXJuIGBzZWxmYAogICAgICovCiAgICBmdW5jdGlvbiBiZXlvbmQoc2xpY2UgbWVtb3J5IHNlbGYsIHNsaWNlIG1lbW9yeSBuZWVkbGUpIGludGVybmFsIHB1cmUgcmV0dXJucyAoc2xpY2UgbWVtb3J5KSB7CiAgICAgICAgaWYgKHNlbGYuX2xlbiA8IG5lZWRsZS5fbGVuKSB7CiAgICAgICAgICAgIHJldHVybiBzZWxmOwogICAgICAgIH0KCiAgICAgICAgYm9vbCBlcXVhbCA9IHRydWU7CiAgICAgICAgaWYgKHNlbGYuX3B0ciAhPSBuZWVkbGUuX3B0cikgewogICAgICAgICAgICBhc3NlbWJseSB7CiAgICAgICAgICAgICAgICBsZXQgbGVuZ3RoIDo9IG1sb2FkKG5lZWRsZSkKICAgICAgICAgICAgICAgIGxldCBzZWxmcHRyIDo9IG1sb2FkKGFkZChzZWxmLCAweDIwKSkKICAgICAgICAgICAgICAgIGxldCBuZWVkbGVwdHIgOj0gbWxvYWQoYWRkKG5lZWRsZSwgMHgyMCkpCiAgICAgICAgICAgICAgICBlcXVhbCA6PSBlcShrZWNjYWsyNTYoc2VsZnB0ciwgbGVuZ3RoKSwga2VjY2FrMjU2KG5lZWRsZXB0ciwgbGVuZ3RoKSkKICAgICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgaWYgKGVxdWFsKSB7CiAgICAgICAgICAgIHNlbGYuX2xlbiAtPSBuZWVkbGUuX2xlbjsKICAgICAgICAgICAgc2VsZi5fcHRyICs9IG5lZWRsZS5fbGVuOwogICAgICAgIH0KCiAgICAgICAgcmV0dXJuIHNlbGY7CiAgICB9CgogICAgLyoKICAgICAqIEBkZXYgUmV0dXJucyB0cnVlIGlmIHRoZSBzbGljZSBlbmRzIHdpdGggYG5lZWRsZWAuCiAgICAgKiBAcGFyYW0gc2VsZiBUaGUgc2xpY2UgdG8gb3BlcmF0ZSBvbi4KICAgICAqIEBwYXJhbSBuZWVkbGUgVGhlIHNsaWNlIHRvIHNlYXJjaCBmb3IuCiAgICAgKiBAcmV0dXJuIFRydWUgaWYgdGhlIHNsaWNlIHN0YXJ0cyB3aXRoIHRoZSBwcm92aWRlZCB0ZXh0LCBmYWxzZSBvdGhlcndpc2UuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGVuZHNXaXRoKHNsaWNlIG1lbW9yeSBzZWxmLCBzbGljZSBtZW1vcnkgbmVlZGxlKSBpbnRlcm5hbCBwdXJlIHJldHVybnMgKGJvb2wpIHsKICAgICAgICBpZiAoc2VsZi5fbGVuIDwgbmVlZGxlLl9sZW4pIHsKICAgICAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICAgIH0KCiAgICAgICAgdWludCBzZWxmcHRyID0gc2VsZi5fcHRyICsgc2VsZi5fbGVuIC0gbmVlZGxlLl9sZW47CgogICAgICAgIGlmIChzZWxmcHRyID09IG5lZWRsZS5fcHRyKSB7CiAgICAgICAgICAgIHJldHVybiB0cnVlOwogICAgICAgIH0KCiAgICAgICAgYm9vbCBlcXVhbDsKICAgICAgICBhc3NlbWJseSB7CiAgICAgICAgICAgIGxldCBsZW5ndGggOj0gbWxvYWQobmVlZGxlKQogICAgICAgICAgICBsZXQgbmVlZGxlcHRyIDo9IG1sb2FkKGFkZChuZWVkbGUsIDB4MjApKQogICAgICAgICAgICBlcXVhbCA6PSBlcShrZWNjYWsyNTYoc2VsZnB0ciwgbGVuZ3RoKSwga2VjY2FrMjU2KG5lZWRsZXB0ciwgbGVuZ3RoKSkKICAgICAgICB9CgogICAgICAgIHJldHVybiBlcXVhbDsKICAgIH0KCiAgICAvKgogICAgICogQGRldiBJZiBgc2VsZmAgZW5kcyB3aXRoIGBuZWVkbGVgLCBgbmVlZGxlYCBpcyByZW1vdmVkIGZyb20gdGhlCiAgICAgKiAgICAgIGVuZCBvZiBgc2VsZmAuIE90aGVyd2lzZSwgYHNlbGZgIGlzIHVubW9kaWZpZWQuCiAgICAgKiBAcGFyYW0gc2VsZiBUaGUgc2xpY2UgdG8gb3BlcmF0ZSBvbi4KICAgICAqIEBwYXJhbSBuZWVkbGUgVGhlIHNsaWNlIHRvIHNlYXJjaCBmb3IuCiAgICAgKiBAcmV0dXJuIGBzZWxmYAogICAgICovCiAgICBmdW5jdGlvbiB1bnRpbChzbGljZSBtZW1vcnkgc2VsZiwgc2xpY2UgbWVtb3J5IG5lZWRsZSkgaW50ZXJuYWwgcHVyZSByZXR1cm5zIChzbGljZSBtZW1vcnkpIHsKICAgICAgICBpZiAoc2VsZi5fbGVuIDwgbmVlZGxlLl9sZW4pIHsKICAgICAgICAgICAgcmV0dXJuIHNlbGY7CiAgICAgICAgfQoKICAgICAgICB1aW50IHNlbGZwdHIgPSBzZWxmLl9wdHIgKyBzZWxmLl9sZW4gLSBuZWVkbGUuX2xlbjsKICAgICAgICBib29sIGVxdWFsID0gdHJ1ZTsKICAgICAgICBpZiAoc2VsZnB0ciAhPSBuZWVkbGUuX3B0cikgewogICAgICAgICAgICBhc3NlbWJseSB7CiAgICAgICAgICAgICAgICBsZXQgbGVuZ3RoIDo9IG1sb2FkKG5lZWRsZSkKICAgICAgICAgICAgICAgIGxldCBuZWVkbGVwdHIgOj0gbWxvYWQoYWRkKG5lZWRsZSwgMHgyMCkpCiAgICAgICAgICAgICAgICBlcXVhbCA6PSBlcShrZWNjYWsyNTYoc2VsZnB0ciwgbGVuZ3RoKSwga2VjY2FrMjU2KG5lZWRsZXB0ciwgbGVuZ3RoKSkKICAgICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgaWYgKGVxdWFsKSB7CiAgICAgICAgICAgIHNlbGYuX2xlbiAtPSBuZWVkbGUuX2xlbjsKICAgICAgICB9CgogICAgICAgIHJldHVybiBzZWxmOwogICAgfQoKICAgIC8vIFJldHVybnMgdGhlIG1lbW9yeSBhZGRyZXNzIG9mIHRoZSBmaXJzdCBieXRlIG9mIHRoZSBmaXJzdCBvY2N1cnJlbmNlIG9mCiAgICAvLyBgbmVlZGxlYCBpbiBgc2VsZmAsIG9yIHRoZSBmaXJzdCBieXRlIGFmdGVyIGBzZWxmYCBpZiBub3QgZm91bmQuCiAgICBmdW5jdGlvbiBmaW5kUHRyKHVpbnQgc2VsZmxlbiwgdWludCBzZWxmcHRyLCB1aW50IG5lZWRsZWxlbiwgdWludCBuZWVkbGVwdHIpIHByaXZhdGUgcHVyZSByZXR1cm5zICh1aW50KSB7CiAgICAgICAgdWludCBwdHIgPSBzZWxmcHRyOwogICAgICAgIHVpbnQgaWR4OwoKICAgICAgICBpZiAobmVlZGxlbGVuIDw9IHNlbGZsZW4pIHsKICAgICAgICAgICAgaWYgKG5lZWRsZWxlbiA8PSAzMikgewogICAgICAgICAgICAgICAgYnl0ZXMzMiBtYXNrID0gYnl0ZXMzMih+KDIgKiogKDggKiAoMzIgLSBuZWVkbGVsZW4pKSAtIDEpKTsKCiAgICAgICAgICAgICAgICBieXRlczMyIG5lZWRsZWRhdGE7CiAgICAgICAgICAgICAgICBhc3NlbWJseSB7IG5lZWRsZWRhdGEgOj0gYW5kKG1sb2FkKG5lZWRsZXB0ciksIG1hc2spIH0KCiAgICAgICAgICAgICAgICB1aW50IGVuZCA9IHNlbGZwdHIgKyBzZWxmbGVuIC0gbmVlZGxlbGVuOwogICAgICAgICAgICAgICAgYnl0ZXMzMiBwdHJkYXRhOwogICAgICAgICAgICAgICAgYXNzZW1ibHkgeyBwdHJkYXRhIDo9IGFuZChtbG9hZChwdHIpLCBtYXNrKSB9CgogICAgICAgICAgICAgICAgd2hpbGUgKHB0cmRhdGEgIT0gbmVlZGxlZGF0YSkgewogICAgICAgICAgICAgICAgICAgIGlmIChwdHIgPj0gZW5kKQogICAgICAgICAgICAgICAgICAgICAgICByZXR1cm4gc2VsZnB0ciArIHNlbGZsZW47CiAgICAgICAgICAgICAgICAgICAgcHRyKys7CiAgICAgICAgICAgICAgICAgICAgYXNzZW1ibHkgeyBwdHJkYXRhIDo9IGFuZChtbG9hZChwdHIpLCBtYXNrKSB9CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICByZXR1cm4gcHRyOwogICAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAgICAgLy8gRm9yIGxvbmcgbmVlZGxlcywgdXNlIGhhc2hpbmcKICAgICAgICAgICAgICAgIGJ5dGVzMzIgaGFzaDsKICAgICAgICAgICAgICAgIGFzc2VtYmx5IHsgaGFzaCA6PSBrZWNjYWsyNTYobmVlZGxlcHRyLCBuZWVkbGVsZW4pIH0KCiAgICAgICAgICAgICAgICBmb3IgKGlkeCA9IDA7IGlkeCA8PSBzZWxmbGVuIC0gbmVlZGxlbGVuOyBpZHgrKykgewogICAgICAgICAgICAgICAgICAgIGJ5dGVzMzIgdGVzdEhhc2g7CiAgICAgICAgICAgICAgICAgICAgYXNzZW1ibHkgeyB0ZXN0SGFzaCA6PSBrZWNjYWsyNTYocHRyLCBuZWVkbGVsZW4pIH0KICAgICAgICAgICAgICAgICAgICBpZiAoaGFzaCA9PSB0ZXN0SGFzaCkKICAgICAgICAgICAgICAgICAgICAgICAgcmV0dXJuIHB0cjsKICAgICAgICAgICAgICAgICAgICBwdHIgKz0gMTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgIH0KICAgICAgICByZXR1cm4gc2VsZnB0ciArIHNlbGZsZW47CiAgICB9CgogICAgLy8gUmV0dXJucyB0aGUgbWVtb3J5IGFkZHJlc3Mgb2YgdGhlIGZpcnN0IGJ5dGUgYWZ0ZXIgdGhlIGxhc3Qgb2NjdXJyZW5jZSBvZgogICAgLy8gYG5lZWRsZWAgaW4gYHNlbGZgLCBvciB0aGUgYWRkcmVzcyBvZiBgc2VsZmAgaWYgbm90IGZvdW5kLgogICAgZnVuY3Rpb24gcmZpbmRQdHIodWludCBzZWxmbGVuLCB1aW50IHNlbGZwdHIsIHVpbnQgbmVlZGxlbGVuLCB1aW50IG5lZWRsZXB0cikgcHJpdmF0ZSBwdXJlIHJldHVybnMgKHVpbnQpIHsKICAgICAgICB1aW50IHB0cjsKCiAgICAgICAgaWYgKG5lZWRsZWxlbiA8PSBzZWxmbGVuKSB7CiAgICAgICAgICAgIGlmIChuZWVkbGVsZW4gPD0gMzIpIHsKICAgICAgICAgICAgICAgIGJ5dGVzMzIgbWFzayA9IGJ5dGVzMzIofigyICoqICg4ICogKDMyIC0gbmVlZGxlbGVuKSkgLSAxKSk7CgogICAgICAgICAgICAgICAgYnl0ZXMzMiBuZWVkbGVkYXRhOwogICAgICAgICAgICAgICAgYXNzZW1ibHkgeyBuZWVkbGVkYXRhIDo9IGFuZChtbG9hZChuZWVkbGVwdHIpLCBtYXNrKSB9CgogICAgICAgICAgICAgICAgcHRyID0gc2VsZnB0ciArIHNlbGZsZW4gLSBuZWVkbGVsZW47CiAgICAgICAgICAgICAgICBieXRlczMyIHB0cmRhdGE7CiAgICAgICAgICAgICAgICBhc3NlbWJseSB7IHB0cmRhdGEgOj0gYW5kKG1sb2FkKHB0ciksIG1hc2spIH0KCiAgICAgICAgICAgICAgICB3aGlsZSAocHRyZGF0YSAhPSBuZWVkbGVkYXRhKSB7CiAgICAgICAgICAgICAgICAgICAgaWYgKHB0ciA8PSBzZWxmcHRyKQogICAgICAgICAgICAgICAgICAgICAgICByZXR1cm4gc2VsZnB0cjsKICAgICAgICAgICAgICAgICAgICBwdHItLTsKICAgICAgICAgICAgICAgICAgICBhc3NlbWJseSB7IHB0cmRhdGEgOj0gYW5kKG1sb2FkKHB0ciksIG1hc2spIH0KICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIHJldHVybiBwdHIgKyBuZWVkbGVsZW47CiAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgICAvLyBGb3IgbG9uZyBuZWVkbGVzLCB1c2UgaGFzaGluZwogICAgICAgICAgICAgICAgYnl0ZXMzMiBoYXNoOwogICAgICAgICAgICAgICAgYXNzZW1ibHkgeyBoYXNoIDo9IGtlY2NhazI1NihuZWVkbGVwdHIsIG5lZWRsZWxlbikgfQogICAgICAgICAgICAgICAgcHRyID0gc2VsZnB0ciArIChzZWxmbGVuIC0gbmVlZGxlbGVuKTsKICAgICAgICAgICAgICAgIHdoaWxlIChwdHIgPj0gc2VsZnB0cikgewogICAgICAgICAgICAgICAgICAgIGJ5dGVzMzIgdGVzdEhhc2g7CiAgICAgICAgICAgICAgICAgICAgYXNzZW1ibHkgeyB0ZXN0SGFzaCA6PSBrZWNjYWsyNTYocHRyLCBuZWVkbGVsZW4pIH0KICAgICAgICAgICAgICAgICAgICBpZiAoaGFzaCA9PSB0ZXN0SGFzaCkKICAgICAgICAgICAgICAgICAgICAgICAgcmV0dXJuIHB0ciArIG5lZWRsZWxlbjsKICAgICAgICAgICAgICAgICAgICBwdHIgLT0gMTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgIH0KICAgICAgICByZXR1cm4gc2VsZnB0cjsKICAgIH0KCiAgICAvKgogICAgICogQGRldiBNb2RpZmllcyBgc2VsZmAgdG8gY29udGFpbiBldmVyeXRoaW5nIGZyb20gdGhlIGZpcnN0IG9jY3VycmVuY2Ugb2YKICAgICAqICAgICAgYG5lZWRsZWAgdG8gdGhlIGVuZCBvZiB0aGUgc2xpY2UuIGBzZWxmYCBpcyBzZXQgdG8gdGhlIGVtcHR5IHNsaWNlCiAgICAgKiAgICAgIGlmIGBuZWVkbGVgIGlzIG5vdCBmb3VuZC4KICAgICAqIEBwYXJhbSBzZWxmIFRoZSBzbGljZSB0byBzZWFyY2ggYW5kIG1vZGlmeS4KICAgICAqIEBwYXJhbSBuZWVkbGUgVGhlIHRleHQgdG8gc2VhcmNoIGZvci4KICAgICAqIEByZXR1cm4gYHNlbGZgLgogICAgICovCiAgICBmdW5jdGlvbiBmaW5kKHNsaWNlIG1lbW9yeSBzZWxmLCBzbGljZSBtZW1vcnkgbmVlZGxlKSBpbnRlcm5hbCBwdXJlIHJldHVybnMgKHNsaWNlIG1lbW9yeSkgewogICAgICAgIHVpbnQgcHRyID0gZmluZFB0cihzZWxmLl9sZW4sIHNlbGYuX3B0ciwgbmVlZGxlLl9sZW4sIG5lZWRsZS5fcHRyKTsKICAgICAgICBzZWxmLl9sZW4gLT0gcHRyIC0gc2VsZi5fcHRyOwogICAgICAgIHNlbGYuX3B0ciA9IHB0cjsKICAgICAgICByZXR1cm4gc2VsZjsKICAgIH0KCiAgICAvKgogICAgICogQGRldiBNb2RpZmllcyBgc2VsZmAgdG8gY29udGFpbiB0aGUgcGFydCBvZiB0aGUgc3RyaW5nIGZyb20gdGhlIHN0YXJ0IG9mCiAgICAgKiAgICAgIGBzZWxmYCB0byB0aGUgZW5kIG9mIHRoZSBmaXJzdCBvY2N1cnJlbmNlIG9mIGBuZWVkbGVgLiBJZiBgbmVlZGxlYAogICAgICogICAgICBpcyBub3QgZm91bmQsIGBzZWxmYCBpcyBzZXQgdG8gdGhlIGVtcHR5IHNsaWNlLgogICAgICogQHBhcmFtIHNlbGYgVGhlIHNsaWNlIHRvIHNlYXJjaCBhbmQgbW9kaWZ5LgogICAgICogQHBhcmFtIG5lZWRsZSBUaGUgdGV4dCB0byBzZWFyY2ggZm9yLgogICAgICogQHJldHVybiBgc2VsZmAuCiAgICAgKi8KICAgIGZ1bmN0aW9uIHJmaW5kKHNsaWNlIG1lbW9yeSBzZWxmLCBzbGljZSBtZW1vcnkgbmVlZGxlKSBpbnRlcm5hbCBwdXJlIHJldHVybnMgKHNsaWNlIG1lbW9yeSkgewogICAgICAgIHVpbnQgcHRyID0gcmZpbmRQdHIoc2VsZi5fbGVuLCBzZWxmLl9wdHIsIG5lZWRsZS5fbGVuLCBuZWVkbGUuX3B0cik7CiAgICAgICAgc2VsZi5fbGVuID0gcHRyIC0gc2VsZi5fcHRyOwogICAgICAgIHJldHVybiBzZWxmOwogICAgfQoKICAgIC8qCiAgICAgKiBAZGV2IFNwbGl0cyB0aGUgc2xpY2UsIHNldHRpbmcgYHNlbGZgIHRvIGV2ZXJ5dGhpbmcgYWZ0ZXIgdGhlIGZpcnN0CiAgICAgKiAgICAgIG9jY3VycmVuY2Ugb2YgYG5lZWRsZWAsIGFuZCBgdG9rZW5gIHRvIGV2ZXJ5dGhpbmcgYmVmb3JlIGl0LiBJZgogICAgICogICAgICBgbmVlZGxlYCBkb2VzIG5vdCBvY2N1ciBpbiBgc2VsZmAsIGBzZWxmYCBpcyBzZXQgdG8gdGhlIGVtcHR5IHNsaWNlLAogICAgICogICAgICBhbmQgYHRva2VuYCBpcyBzZXQgdG8gdGhlIGVudGlyZXR5IG9mIGBzZWxmYC4KICAgICAqIEBwYXJhbSBzZWxmIFRoZSBzbGljZSB0byBzcGxpdC4KICAgICAqIEBwYXJhbSBuZWVkbGUgVGhlIHRleHQgdG8gc2VhcmNoIGZvciBpbiBgc2VsZmAuCiAgICAgKiBAcGFyYW0gdG9rZW4gQW4gb3V0cHV0IHBhcmFtZXRlciB0byB3aGljaCB0aGUgZmlyc3QgdG9rZW4gaXMgd3JpdHRlbi4KICAgICAqIEByZXR1cm4gYHRva2VuYC4KICAgICAqLwogICAgZnVuY3Rpb24gc3BsaXQoc2xpY2UgbWVtb3J5IHNlbGYsIHNsaWNlIG1lbW9yeSBuZWVkbGUsIHNsaWNlIG1lbW9yeSB0b2tlbikgaW50ZXJuYWwgcHVyZSByZXR1cm5zIChzbGljZSBtZW1vcnkpIHsKICAgICAgICB1aW50IHB0ciA9IGZpbmRQdHIoc2VsZi5fbGVuLCBzZWxmLl9wdHIsIG5lZWRsZS5fbGVuLCBuZWVkbGUuX3B0cik7CiAgICAgICAgdG9rZW4uX3B0ciA9IHNlbGYuX3B0cjsKICAgICAgICB0b2tlbi5fbGVuID0gcHRyIC0gc2VsZi5fcHRyOwogICAgICAgIGlmIChwdHIgPT0gc2VsZi5fcHRyICsgc2VsZi5fbGVuKSB7CiAgICAgICAgICAgIC8vIE5vdCBmb3VuZAogICAgICAgICAgICBzZWxmLl9sZW4gPSAwOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIHNlbGYuX2xlbiAtPSB0b2tlbi5fbGVuICsgbmVlZGxlLl9sZW47CiAgICAgICAgICAgIHNlbGYuX3B0ciA9IHB0ciArIG5lZWRsZS5fbGVuOwogICAgICAgIH0KICAgICAgICByZXR1cm4gdG9rZW47CiAgICB9CgogICAgLyoKICAgICAqIEBkZXYgU3BsaXRzIHRoZSBzbGljZSwgc2V0dGluZyBgc2VsZmAgdG8gZXZlcnl0aGluZyBhZnRlciB0aGUgZmlyc3QKICAgICAqICAgICAgb2NjdXJyZW5jZSBvZiBgbmVlZGxlYCwgYW5kIHJldHVybmluZyBldmVyeXRoaW5nIGJlZm9yZSBpdC4gSWYKICAgICAqICAgICAgYG5lZWRsZWAgZG9lcyBub3Qgb2NjdXIgaW4gYHNlbGZgLCBgc2VsZmAgaXMgc2V0IHRvIHRoZSBlbXB0eSBzbGljZSwKICAgICAqICAgICAgYW5kIHRoZSBlbnRpcmV0eSBvZiBgc2VsZmAgaXMgcmV0dXJuZWQuCiAgICAgKiBAcGFyYW0gc2VsZiBUaGUgc2xpY2UgdG8gc3BsaXQuCiAgICAgKiBAcGFyYW0gbmVlZGxlIFRoZSB0ZXh0IHRvIHNlYXJjaCBmb3IgaW4gYHNlbGZgLgogICAgICogQHJldHVybiBUaGUgcGFydCBvZiBgc2VsZmAgdXAgdG8gdGhlIGZpcnN0IG9jY3VycmVuY2Ugb2YgYGRlbGltYC4KICAgICAqLwogICAgZnVuY3Rpb24gc3BsaXQoc2xpY2UgbWVtb3J5IHNlbGYsIHNsaWNlIG1lbW9yeSBuZWVkbGUpIGludGVybmFsIHB1cmUgcmV0dXJucyAoc2xpY2UgbWVtb3J5IHRva2VuKSB7CiAgICAgICAgc3BsaXQoc2VsZiwgbmVlZGxlLCB0b2tlbik7CiAgICB9CgogICAgLyoKICAgICAqIEBkZXYgU3BsaXRzIHRoZSBzbGljZSwgc2V0dGluZyBgc2VsZmAgdG8gZXZlcnl0aGluZyBiZWZvcmUgdGhlIGxhc3QKICAgICAqICAgICAgb2NjdXJyZW5jZSBvZiBgbmVlZGxlYCwgYW5kIGB0b2tlbmAgdG8gZXZlcnl0aGluZyBhZnRlciBpdC4gSWYKICAgICAqICAgICAgYG5lZWRsZWAgZG9lcyBub3Qgb2NjdXIgaW4gYHNlbGZgLCBgc2VsZmAgaXMgc2V0IHRvIHRoZSBlbXB0eSBzbGljZSwKICAgICAqICAgICAgYW5kIGB0b2tlbmAgaXMgc2V0IHRvIHRoZSBlbnRpcmV0eSBvZiBgc2VsZmAuCiAgICAgKiBAcGFyYW0gc2VsZiBUaGUgc2xpY2UgdG8gc3BsaXQuCiAgICAgKiBAcGFyYW0gbmVlZGxlIFRoZSB0ZXh0IHRvIHNlYXJjaCBmb3IgaW4gYHNlbGZgLgogICAgICogQHBhcmFtIHRva2VuIEFuIG91dHB1dCBwYXJhbWV0ZXIgdG8gd2hpY2ggdGhlIGZpcnN0IHRva2VuIGlzIHdyaXR0ZW4uCiAgICAgKiBAcmV0dXJuIGB0b2tlbmAuCiAgICAgKi8KICAgIGZ1bmN0aW9uIHJzcGxpdChzbGljZSBtZW1vcnkgc2VsZiwgc2xpY2UgbWVtb3J5IG5lZWRsZSwgc2xpY2UgbWVtb3J5IHRva2VuKSBpbnRlcm5hbCBwdXJlIHJldHVybnMgKHNsaWNlIG1lbW9yeSkgewogICAgICAgIHVpbnQgcHRyID0gcmZpbmRQdHIoc2VsZi5fbGVuLCBzZWxmLl9wdHIsIG5lZWRsZS5fbGVuLCBuZWVkbGUuX3B0cik7CiAgICAgICAgdG9rZW4uX3B0ciA9IHB0cjsKICAgICAgICB0b2tlbi5fbGVuID0gc2VsZi5fbGVuIC0gKHB0ciAtIHNlbGYuX3B0cik7CiAgICAgICAgaWYgKHB0ciA9PSBzZWxmLl9wdHIpIHsKICAgICAgICAgICAgLy8gTm90IGZvdW5kCiAgICAgICAgICAgIHNlbGYuX2xlbiA9IDA7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgc2VsZi5fbGVuIC09IHRva2VuLl9sZW4gKyBuZWVkbGUuX2xlbjsKICAgICAgICB9CiAgICAgICAgcmV0dXJuIHRva2VuOwogICAgfQoKICAgIC8qCiAgICAgKiBAZGV2IFNwbGl0cyB0aGUgc2xpY2UsIHNldHRpbmcgYHNlbGZgIHRvIGV2ZXJ5dGhpbmcgYmVmb3JlIHRoZSBsYXN0CiAgICAgKiAgICAgIG9jY3VycmVuY2Ugb2YgYG5lZWRsZWAsIGFuZCByZXR1cm5pbmcgZXZlcnl0aGluZyBhZnRlciBpdC4gSWYKICAgICAqICAgICAgYG5lZWRsZWAgZG9lcyBub3Qgb2NjdXIgaW4gYHNlbGZgLCBgc2VsZmAgaXMgc2V0IHRvIHRoZSBlbXB0eSBzbGljZSwKICAgICAqICAgICAgYW5kIHRoZSBlbnRpcmV0eSBvZiBgc2VsZmAgaXMgcmV0dXJuZWQuCiAgICAgKiBAcGFyYW0gc2VsZiBUaGUgc2xpY2UgdG8gc3BsaXQuCiAgICAgKiBAcGFyYW0gbmVlZGxlIFRoZSB0ZXh0IHRvIHNlYXJjaCBmb3IgaW4gYHNlbGZgLgogICAgICogQHJldHVybiBUaGUgcGFydCBvZiBgc2VsZmAgYWZ0ZXIgdGhlIGxhc3Qgb2NjdXJyZW5jZSBvZiBgZGVsaW1gLgogICAgICovCiAgICBmdW5jdGlvbiByc3BsaXQoc2xpY2UgbWVtb3J5IHNlbGYsIHNsaWNlIG1lbW9yeSBuZWVkbGUpIGludGVybmFsIHB1cmUgcmV0dXJucyAoc2xpY2UgbWVtb3J5IHRva2VuKSB7CiAgICAgICAgcnNwbGl0KHNlbGYsIG5lZWRsZSwgdG9rZW4pOwogICAgfQoKICAgIC8qCiAgICAgKiBAZGV2IENvdW50cyB0aGUgbnVtYmVyIG9mIG5vbm92ZXJsYXBwaW5nIG9jY3VycmVuY2VzIG9mIGBuZWVkbGVgIGluIGBzZWxmYC4KICAgICAqIEBwYXJhbSBzZWxmIFRoZSBzbGljZSB0byBzZWFyY2guCiAgICAgKiBAcGFyYW0gbmVlZGxlIFRoZSB0ZXh0IHRvIHNlYXJjaCBmb3IgaW4gYHNlbGZgLgogICAgICogQHJldHVybiBUaGUgbnVtYmVyIG9mIG9jY3VycmVuY2VzIG9mIGBuZWVkbGVgIGZvdW5kIGluIGBzZWxmYC4KICAgICAqLwogICAgZnVuY3Rpb24gY291bnQoc2xpY2UgbWVtb3J5IHNlbGYsIHNsaWNlIG1lbW9yeSBuZWVkbGUpIGludGVybmFsIHB1cmUgcmV0dXJucyAodWludCBjbnQpIHsKICAgICAgICB1aW50IHB0ciA9IGZpbmRQdHIoc2VsZi5fbGVuLCBzZWxmLl9wdHIsIG5lZWRsZS5fbGVuLCBuZWVkbGUuX3B0cikgKyBuZWVkbGUuX2xlbjsKICAgICAgICB3aGlsZSAocHRyIDw9IHNlbGYuX3B0ciArIHNlbGYuX2xlbikgewogICAgICAgICAgICBjbnQrKzsKICAgICAgICAgICAgcHRyID0gZmluZFB0cihzZWxmLl9sZW4gLSAocHRyIC0gc2VsZi5fcHRyKSwgcHRyLCBuZWVkbGUuX2xlbiwgbmVlZGxlLl9wdHIpICsgbmVlZGxlLl9sZW47CiAgICAgICAgfQogICAgfQoKICAgIC8qCiAgICAgKiBAZGV2IFJldHVybnMgVHJ1ZSBpZiBgc2VsZmAgY29udGFpbnMgYG5lZWRsZWAuCiAgICAgKiBAcGFyYW0gc2VsZiBUaGUgc2xpY2UgdG8gc2VhcmNoLgogICAgICogQHBhcmFtIG5lZWRsZSBUaGUgdGV4dCB0byBzZWFyY2ggZm9yIGluIGBzZWxmYC4KICAgICAqIEByZXR1cm4gVHJ1ZSBpZiBgbmVlZGxlYCBpcyBmb3VuZCBpbiBgc2VsZmAsIGZhbHNlIG90aGVyd2lzZS4KICAgICAqLwogICAgZnVuY3Rpb24gY29udGFpbnMoc2xpY2UgbWVtb3J5IHNlbGYsIHNsaWNlIG1lbW9yeSBuZWVkbGUpIGludGVybmFsIHB1cmUgcmV0dXJucyAoYm9vbCkgewogICAgICAgIHJldHVybiByZmluZFB0cihzZWxmLl9sZW4sIHNlbGYuX3B0ciwgbmVlZGxlLl9sZW4sIG5lZWRsZS5fcHRyKSAhPSBzZWxmLl9wdHI7CiAgICB9CgogICAgLyoKICAgICAqIEBkZXYgUmV0dXJucyBhIG5ld2x5IGFsbG9jYXRlZCBzdHJpbmcgY29udGFpbmluZyB0aGUgY29uY2F0ZW5hdGlvbiBvZgogICAgICogICAgICBgc2VsZmAgYW5kIGBvdGhlcmAuCiAgICAgKiBAcGFyYW0gc2VsZiBUaGUgZmlyc3Qgc2xpY2UgdG8gY29uY2F0ZW5hdGUuCiAgICAgKiBAcGFyYW0gb3RoZXIgVGhlIHNlY29uZCBzbGljZSB0byBjb25jYXRlbmF0ZS4KICAgICAqIEByZXR1cm4gVGhlIGNvbmNhdGVuYXRpb24gb2YgdGhlIHR3byBzdHJpbmdzLgogICAgICovCiAgICBmdW5jdGlvbiBjb25jYXQoc2xpY2UgbWVtb3J5IHNlbGYsIHNsaWNlIG1lbW9yeSBvdGhlcikgaW50ZXJuYWwgcHVyZSByZXR1cm5zIChzdHJpbmcgbWVtb3J5KSB7CiAgICAgICAgc3RyaW5nIG1lbW9yeSByZXQgPSBuZXcgc3RyaW5nKHNlbGYuX2xlbiArIG90aGVyLl9sZW4pOwogICAgICAgIHVpbnQgcmV0cHRyOwogICAgICAgIGFzc2VtYmx5IHsgcmV0cHRyIDo9IGFkZChyZXQsIDMyKSB9CiAgICAgICAgbWVtY3B5KHJldHB0ciwgc2VsZi5fcHRyLCBzZWxmLl9sZW4pOwogICAgICAgIG1lbWNweShyZXRwdHIgKyBzZWxmLl9sZW4sIG90aGVyLl9wdHIsIG90aGVyLl9sZW4pOwogICAgICAgIHJldHVybiByZXQ7CiAgICB9CgogICAgLyoKICAgICAqIEBkZXYgSm9pbnMgYW4gYXJyYXkgb2Ygc2xpY2VzLCB1c2luZyBgc2VsZmAgYXMgYSBkZWxpbWl0ZXIsIHJldHVybmluZyBhCiAgICAgKiAgICAgIG5ld2x5IGFsbG9jYXRlZCBzdHJpbmcuCiAgICAgKiBAcGFyYW0gc2VsZiBUaGUgZGVsaW1pdGVyIHRvIHVzZS4KICAgICAqIEBwYXJhbSBwYXJ0cyBBIGxpc3Qgb2Ygc2xpY2VzIHRvIGpvaW4uCiAgICAgKiBAcmV0dXJuIEEgbmV3bHkgYWxsb2NhdGVkIHN0cmluZyBjb250YWluaW5nIGFsbCB0aGUgc2xpY2VzIGluIGBwYXJ0c2AsCiAgICAgKiAgICAgICAgIGpvaW5lZCB3aXRoIGBzZWxmYC4KICAgICAqLwogICAgZnVuY3Rpb24gam9pbihzbGljZSBtZW1vcnkgc2VsZiwgc2xpY2VbXSBtZW1vcnkgcGFydHMpIGludGVybmFsIHB1cmUgcmV0dXJucyAoc3RyaW5nIG1lbW9yeSkgewogICAgICAgIGlmIChwYXJ0cy5sZW5ndGggPT0gMCkKICAgICAgICAgICAgcmV0dXJuICIiOwoKICAgICAgICB1aW50IGxlbmd0aCA9IHNlbGYuX2xlbiAqIChwYXJ0cy5sZW5ndGggLSAxKTsKICAgICAgICBmb3IodWludCBpID0gMDsgaSA8IHBhcnRzLmxlbmd0aDsgaSsrKQogICAgICAgICAgICBsZW5ndGggKz0gcGFydHNbaV0uX2xlbjsKCiAgICAgICAgc3RyaW5nIG1lbW9yeSByZXQgPSBuZXcgc3RyaW5nKGxlbmd0aCk7CiAgICAgICAgdWludCByZXRwdHI7CiAgICAgICAgYXNzZW1ibHkgeyByZXRwdHIgOj0gYWRkKHJldCwgMzIpIH0KCiAgICAgICAgZm9yKGkgPSAwOyBpIDwgcGFydHMubGVuZ3RoOyBpKyspIHsKICAgICAgICAgICAgbWVtY3B5KHJldHB0ciwgcGFydHNbaV0uX3B0ciwgcGFydHNbaV0uX2xlbik7CiAgICAgICAgICAgIHJldHB0ciArPSBwYXJ0c1tpXS5fbGVuOwogICAgICAgICAgICBpZiAoaSA8IHBhcnRzLmxlbmd0aCAtIDEpIHsKICAgICAgICAgICAgICAgIG1lbWNweShyZXRwdHIsIHNlbGYuX3B0ciwgc2VsZi5fbGVuKTsKICAgICAgICAgICAgICAgIHJldHB0ciArPSBzZWxmLl9sZW47CiAgICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIHJldHVybiByZXQ7CiAgICB9Cn0K";
    public static final String TABLE_SOURCE = "cHJhZ21hIHNvbGlkaXR5IF4wLjQuMjU7DQoNCmNvbnRyYWN0IFRhYmxlRmFjdG9yeSB7DQogICAgZnVuY3Rpb24gb3BlblRhYmxlKHN0cmluZykgcHVibGljIGNvbnN0YW50IHJldHVybnMgKFRhYmxlKTsgIC8vIOaJk+W8gOihqA0KICAgIGZ1bmN0aW9uIGNyZWF0ZVRhYmxlKHN0cmluZyxzdHJpbmcsc3RyaW5nKSBwdWJsaWMgcmV0dXJucyhpbnQpOyAgLy8g5Yib5bu66KGoDQp9DQoNCi8vIOafpeivouadoeS7tg0KY29udHJhY3QgQ29uZGl0aW9uIHsNCiAgICAvL+etieS6jg0KICAgIGZ1bmN0aW9uIEVRKHN0cmluZywgaW50KSBwdWJsaWM7DQogICAgZnVuY3Rpb24gRVEoc3RyaW5nLCBzdHJpbmcpIHB1YmxpYzsNCg0KICAgIC8v5LiN562J5LqODQogICAgZnVuY3Rpb24gTkUoc3RyaW5nLCBpbnQpIHB1YmxpYzsNCiAgICBmdW5jdGlvbiBORShzdHJpbmcsIHN0cmluZykgIHB1YmxpYzsNCg0KICAgIC8v5aSn5LqODQogICAgZnVuY3Rpb24gR1Qoc3RyaW5nLCBpbnQpIHB1YmxpYzsNCiAgICAvL+Wkp+S6juaIluetieS6jg0KICAgIGZ1bmN0aW9uIEdFKHN0cmluZywgaW50KSBwdWJsaWM7DQoNCiAgICAvL+Wwj+S6jg0KICAgIGZ1bmN0aW9uIExUKHN0cmluZywgaW50KSBwdWJsaWM7DQogICAgLy/lsI/kuo7miJbnrYnkuo4NCiAgICBmdW5jdGlvbiBMRShzdHJpbmcsIGludCkgcHVibGljOw0KDQogICAgLy/pmZDliLbov5Tlm57orrDlvZXmnaHmlbANCiAgICBmdW5jdGlvbiBsaW1pdChpbnQpIHB1YmxpYzsNCiAgICBmdW5jdGlvbiBsaW1pdChpbnQsIGludCkgcHVibGljOw0KfQ0KDQovLyDljZXmnaHmlbDmja7orrDlvZUNCmNvbnRyYWN0IEVudHJ5IHsNCiAgICBmdW5jdGlvbiBnZXRJbnQoc3RyaW5nKSBwdWJsaWMgY29uc3RhbnQgcmV0dXJucyhpbnQpOw0KICAgIGZ1bmN0aW9uIGdldEFkZHJlc3Moc3RyaW5nKSBwdWJsaWMgY29uc3RhbnQgcmV0dXJucyhhZGRyZXNzKTsNCiAgICBmdW5jdGlvbiBnZXRCeXRlczY0KHN0cmluZykgcHVibGljIGNvbnN0YW50IHJldHVybnMoYnl0ZVs2NF0pOw0KICAgIGZ1bmN0aW9uIGdldEJ5dGVzMzIoc3RyaW5nKSBwdWJsaWMgY29uc3RhbnQgcmV0dXJucyhieXRlczMyKTsNCiAgICBmdW5jdGlvbiBnZXRTdHJpbmcoc3RyaW5nKSBwdWJsaWMgY29uc3RhbnQgcmV0dXJucyhzdHJpbmcpOw0KDQogICAgZnVuY3Rpb24gc2V0KHN0cmluZywgaW50KSBwdWJsaWM7DQogICAgZnVuY3Rpb24gc2V0KHN0cmluZywgc3RyaW5nKSBwdWJsaWM7DQogICAgZnVuY3Rpb24gc2V0KHN0cmluZywgYWRkcmVzcykgcHVibGljOw0KfQ0KDQovLyDmlbDmja7orrDlvZXpm4YNCmNvbnRyYWN0IEVudHJpZXMgew0KICAgIGZ1bmN0aW9uIGdldChpbnQpIHB1YmxpYyBjb25zdGFudCByZXR1cm5zKEVudHJ5KTsNCiAgICBmdW5jdGlvbiBzaXplKCkgcHVibGljIGNvbnN0YW50IHJldHVybnMoaW50KTsNCn0NCg0KLy8gVGFibGXkuLvnsbsNCmNvbnRyYWN0IFRhYmxlIHsNCiAgICAvLyDmn6Xor6LmjqXlj6MNCiAgICBmdW5jdGlvbiBzZWxlY3Qoc3RyaW5nLCBDb25kaXRpb24pIHB1YmxpYyBjb25zdGFudCByZXR1cm5zKEVudHJpZXMpOw0KICAgIC8vIOaPkuWFpeaOpeWPow0KICAgIGZ1bmN0aW9uIGluc2VydChzdHJpbmcsIEVudHJ5KSBwdWJsaWMgcmV0dXJucyhpbnQpOw0KICAgIC8vIOabtOaWsOaOpeWPow0KICAgIGZ1bmN0aW9uIHVwZGF0ZShzdHJpbmcsIEVudHJ5LCBDb25kaXRpb24pIHB1YmxpYyByZXR1cm5zKGludCk7DQogICAgLy8g5Yig6Zmk5o6l5Y+jDQogICAgZnVuY3Rpb24gcmVtb3ZlKHN0cmluZywgQ29uZGl0aW9uKSBwdWJsaWMgcmV0dXJucyhpbnQpOw0KDQogICAgZnVuY3Rpb24gbmV3RW50cnkoKSBwdWJsaWMgY29uc3RhbnQgcmV0dXJucyhFbnRyeSk7DQogICAgZnVuY3Rpb24gbmV3Q29uZGl0aW9uKCkgcHVibGljIGNvbnN0YW50IHJldHVybnMoQ29uZGl0aW9uKTsNCn0=";


    public static final String PROXY_MD = "# 代理合约模板\n" +
            "\n" +
            "\n" +
            "本合约模板由深圳前海股权交易中心贡献，针对数据上链编写的通用代理存储合约。\n" +
            "\n" +
            "## 简介\n" +
            "代理合约利用solidity的fallback功能，包含EnrollProxy（代理合约），EnrollController（业务合约），EnrollStorage（存储合约）。\n" +
            "\n" +
            "- 代理合约对外交互接口\n" +
            "- 业务合约实现业务逻辑\n" +
            "- 存储合约完成数据存储\n" +
            "\n" +
            "EnrollProxy合约通过Fallback机制调用EnrollController合约的函数进行数据上链（通过EnrollProxy合约地址结合使用EnrollController合约的ABI，操作EnrollController合约的函数），其带来的优点包括：\n" +
            "\n" +
            "- 区块链应用的业务层只与EnrollProxy合约进行交互，EnrollProxy合约不会升级，地址不会变化。\n" +
            "\n" +
            "- 后续中业务或存储需求导致业务合约或存储合约需要升级，则升级EnrollController和EnrollStorage合约，达到数据、业务逻辑解耦的效果。\n" +
            "\n" +
            "*期待你一起完善合约模板中的权限控制逻辑*\n" +
            "\n" +
            "## 合约架构说明\n" +
            "\n" +
            "```java\n" +
            "EnrollProxy\n" +
            "\t继承EnrollStorageStateful\n" +
            "\t继承Proxy（继承Ownable）　\n" +
            "    \n" +
            "EnrollController\n" +
            "\t继承EnrollStorageStateful\n" +
            "\t继承Ownable\n" +
            "\n" +
            "EnrollStorageStateful\n" +
            "\t包含成员enrollStorage，EnrollStorage合约实例\n" +
            "\n" +
            "由于是继承的关系，EnrollProxy合约和EnrollController合约的存储空间排列是一样的，所以可通过EnrollProxy执行fallback操作。  \n" +
            "\n" +
            "enrollStorage是EnrollStorageStateful合约中的成员，所以enrollStorage合约与EnrollStorageStateful合约存储空间排布是不一样。\n" +
            "```\n" +
            "\n" +
            "## 使用说明\n" +
            "1. 编译部署EnrollProxy，EnrollController，EnrollStorage合约。\n" +
            "2. 配置代理合约：\n" +
            "   1. 存储合约合约：调用EnrollProxy合约setStorage函数，参数为EnrollStorage合约地址。\n" +
            "   2. 配置业务合约：调用EnrollProxy合约upgradeTo函数，参数为：合约版本号，EnrollController合约地址。\n" +
            "3. 设置存储合约的代理地址：调用EnrollStorage合约setProxy函数，参数为EnrollProxy合约地址。\n" +
            "       \n" +
            "\n" +
            "完成以上步骤后，就可以通过EnrollProxy合约地址，结合业务合约EnrollController合约的ABI，操作EnrollController合约的业务函数。\n" +
            "\n" +
            "\n";

}
